From c6f71fdc2458cc07fad93c6898471e1230af5aa4 Mon Sep 17 00:00:00 2001 From: Benjamin Gaussorgues Date: Thu, 9 Nov 2023 15:06:42 +0100 Subject: [PATCH 01/17] Add Content-Type response header for JSON responses Initial work in #90 Signed-off-by: Benjamin Gaussorgues --- index.web.php | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/index.web.php b/index.web.php index 48db2b1d..b88d6193 100644 --- a/index.web.php +++ b/index.web.php @@ -54,6 +54,7 @@ public function isAuthenticated(): bool { if (isset($_POST['step'])) { // mark step as failed http_response_code(500); + header('Content-Type: application/json'); echo(json_encode(['proceed' => false, 'response' => $e->getMessage()])); die(); } @@ -140,6 +141,7 @@ public function isAuthenticated(): bool { break; } $updater->endStep($step); + header('Content-Type: application/json'); echo(json_encode(['proceed' => true])); } catch (UpdateException $e) { $data = $e->getData(); @@ -155,6 +157,7 @@ public function isAuthenticated(): bool { $updater->rollbackChanges($step); } http_response_code(500); + header('Content-Type: application/json'); echo(json_encode(['proceed' => false, 'response' => $data])); } catch (\Exception $e) { $message = $e->getMessage(); @@ -170,6 +173,7 @@ public function isAuthenticated(): bool { $updater->rollbackChanges($step); } http_response_code(500); + header('Content-Type: application/json'); echo(json_encode(['proceed' => false, 'response' => $message])); } From 2e4d4dd8c15bace25cfa7ef28e7a3d064121fdd7 Mon Sep 17 00:00:00 2001 From: Benjamin Gaussorgues Date: Thu, 9 Nov 2023 12:16:02 +0100 Subject: [PATCH 02/17] Improve iterators Signed-off-by: Benjamin Gaussorgues --- Makefile | 4 +- index.php | 98 ++++++++++-------- lib/RecursiveDirectoryIteratorFilter.php | 26 +++++ lib/RecursiveDirectoryIteratorWithoutData.php | 29 ------ lib/Updater.php | 68 ++++++------ updater.phar | Bin 1169025 -> 1169341 bytes vendor/composer/autoload_classmap.php | 2 +- vendor/composer/autoload_static.php | 2 +- 8 files changed, 122 insertions(+), 107 deletions(-) create mode 100644 lib/RecursiveDirectoryIteratorFilter.php delete mode 100644 lib/RecursiveDirectoryIteratorWithoutData.php diff --git a/Makefile b/Makefile index 99c2b656..0ef93338 100644 --- a/Makefile +++ b/Makefile @@ -12,11 +12,11 @@ updater.phar: updater.php lib/*.php buildVersionFile.php clean: rm updater.phar index.php -index.php: lib/UpdateException.php lib/LogException.php lib/RecursiveDirectoryIteratorWithoutData.php lib/Updater.php index.web.php +index.php: lib/UpdateException.php lib/LogException.php lib/RecursiveDirectoryIteratorFilter.php lib/Updater.php index.web.php # First put openining php tag and license awk '/^<\?php$$/,/\*\//' index.web.php > index.php # Then concat all files while filtering php tag and license - cat lib/UpdateException.php lib/LogException.php lib/RecursiveDirectoryIteratorWithoutData.php lib/Updater.php index.web.php| grep -v "^namespace" | awk '/^<\?php$$/,/\*\//{next} 1' >> index.php + cat lib/UpdateException.php lib/LogException.php lib/RecursiveDirectoryIteratorFilter.php lib/Updater.php index.web.php| grep -v "^namespace" | awk '/^<\?php$$/,/\*\//{next} 1' >> index.php test/vendor: cd tests && composer install diff --git a/index.php b/index.php index b4048a7b..9bd69f12 100644 --- a/index.php +++ b/index.php @@ -7,6 +7,7 @@ * SPDX-License-Identifier: AGPL-3.0-or-later */ + class UpdateException extends \Exception { /** @param list $data */ @@ -26,28 +27,25 @@ class LogException extends \Exception { } -class RecursiveDirectoryIteratorWithoutData extends \RecursiveFilterIterator { - public function accept(): bool { - $excludes = [ - '.rnd', - '.well-known', - 'data', - '..', - ]; +class RecursiveDirectoryIteratorFilter extends \RecursiveFilterIterator { + private array $excludedPaths; - /** @var \SplFileInfo|false */ - $current = $this->current(); - if (!$current) { - return false; - } + public function __construct( + \RecursiveDirectoryIterator $iterator, + array $excludedPaths = ['data'], + ) { + parent::__construct($iterator); + $this->excludedPaths = array_flip($excludedPaths); + } - return !(in_array($current->getFilename(), $excludes, true) || $current->isDir()); + public function accept(): bool { + return !isset($this->excludedPaths[$this->current()->getFilename()]); } } class Updater { - private string $baseDir; + private string $nextcloudDir; private array $configValues = []; private string $currentVersion = 'unknown'; private string $buildTime; @@ -60,13 +58,15 @@ class Updater { * @param string $baseDir the absolute path to the /updater/ directory in the Nextcloud root * @throws \Exception */ - public function __construct(string $baseDir) { - $this->baseDir = $baseDir; + public function __construct( + private string $baseDir + ) { + $this->nextcloudDir = realpath(dirname($baseDir)); if ($dir = getenv('NEXTCLOUD_CONFIG_DIR')) { - $configFileName = rtrim($dir, '/') . '/config.php'; + $configFileName = realpath($dir . '/config.php'); } else { - $configFileName = $this->baseDir . '/../config/config.php'; + $configFileName = $this->nextcloudDir . '/config/config.php'; } if (!file_exists($configFileName)) { throw new \Exception('Could not find config.php. Is this file in the "updater" subfolder of Nextcloud?'); @@ -87,7 +87,7 @@ public function __construct(string $baseDir) { throw new \Exception('Could not read data directory from config.php.'); } - $versionFileName = $this->baseDir . '/../version.php'; + $versionFileName = $this->nextcloudDir . '/version.php'; if (!file_exists($versionFileName)) { // fallback to version in config.php $version = $this->getConfigOptionString('version'); @@ -118,19 +118,15 @@ public function __construct(string $baseDir) { /** * Returns whether the web updater is disabled - * - * @return bool */ - public function isDisabled() { + public function isDisabled(): bool { return $this->disabled; } /** * Returns current version or "unknown" if this could not be determined. - * - * @return string */ - public function getCurrentVersion() { + public function getCurrentVersion(): string { return $this->currentVersion; } @@ -138,7 +134,7 @@ public function getCurrentVersion() { * Returns currently used release channel */ private function getCurrentReleaseChannel(): string { - return ($this->getConfigOptionString('updater.release.channel') ?? 'stable'); + return $this->getConfigOptionString('updater.release.channel') ?? 'stable'; } /** @@ -310,16 +306,19 @@ private function getAppDirectories(): array { /** * Gets the recursive directory iterator over the Nextcloud folder * - * @return \RecursiveIteratorIterator<\RecursiveDirectoryIterator> + * @return \RecursiveIteratorIterator<\RecursiveDirectoryIterator|RecursiveDirectoryIteratorFilter> */ - private function getRecursiveDirectoryIterator(?string $folder = null): \RecursiveIteratorIterator { + private function getRecursiveDirectoryIterator(?string $folder = null, array $excludedPaths = []): \RecursiveIteratorIterator { if ($folder === null) { $folder = $this->baseDir . '/../'; } - return new \RecursiveIteratorIterator( - new \RecursiveDirectoryIterator($folder, \RecursiveDirectoryIterator::SKIP_DOTS), - \RecursiveIteratorIterator::CHILD_FIRST - ); + + $iterator = new \RecursiveDirectoryIterator($folder, \FilesystemIterator::SKIP_DOTS); + if (!empty($excludedPaths)) { + $iterator = new RecursiveDirectoryIteratorFilter($iterator, $excludedPaths); + } + + return new \RecursiveIteratorIterator($iterator, \RecursiveIteratorIterator::CHILD_FIRST); } /** @@ -330,7 +329,7 @@ public function checkForExpectedFilesAndFolders(): void { $expectedElements = $this->getExpectedElementsList(); $unexpectedElements = []; - foreach (new \DirectoryIterator($this->baseDir . '/../') as $fileInfo) { + foreach (new \DirectoryIterator($this->nextcloudDir) as $fileInfo) { if (array_search($fileInfo->getFilename(), $expectedElements) === false) { $unexpectedElements[] = $fileInfo->getFilename(); } @@ -348,15 +347,21 @@ public function checkForExpectedFilesAndFolders(): void { public function checkWritePermissions(): void { $this->silentLog('[info] checkWritePermissions()'); - $notWritablePaths = array(); - $dir = new \RecursiveDirectoryIterator($this->baseDir . '/../'); - $filter = new RecursiveDirectoryIteratorWithoutData($dir); - /** @var iterable */ - $it = new \RecursiveIteratorIterator($filter); + $excludedPaths = [ + '.rnd' => true, + '.well-known' => true, + 'data' => true, + ]; + + $it = new \DirectoryIterator($this->nextcloudDir); - foreach ($it as $path => $dir) { - if (!is_writable($path)) { - $notWritablePaths[] = $path; + $notWritablePaths = []; + foreach ($it as $path => $fileInfo) { + if ($fileInfo->isDot() || isset($excludedPaths[$fileInfo->getFilename()])) { + continue; + } + if (!$fileInfo->isWritable()) { + $notWritablePaths[] = $fileInfo->getFilename(); } } if (count($notWritablePaths) > 0) { @@ -429,7 +434,7 @@ public function createBackup(): void { * @var string $path * @var \SplFileInfo $fileInfo */ - foreach ($this->getRecursiveDirectoryIterator($currentDir) as $path => $fileInfo) { + foreach ($this->getRecursiveDirectoryIterator($currentDir, $excludedElements) as $path => $fileInfo) { $fileName = explode($currentDir, $path)[1]; $folderStructure = explode('/', $fileName, -1); @@ -958,8 +963,9 @@ public function deleteOldFiles(): void { } /** - * Moves the specified filed except the excluded elements to the correct position + * Moves the specified files except the excluded elements to the correct position * + * @param string[] $excludedElements * @throws \Exception */ private function moveWithExclusions(string $dataLocation, array $excludedElements): void { @@ -1278,6 +1284,7 @@ public function isAuthenticated(): bool { if (isset($_POST['step'])) { // mark step as failed http_response_code(500); + header('Content-Type: application/json'); echo(json_encode(['proceed' => false, 'response' => $e->getMessage()])); die(); } @@ -1364,6 +1371,7 @@ public function isAuthenticated(): bool { break; } $updater->endStep($step); + header('Content-Type: application/json'); echo(json_encode(['proceed' => true])); } catch (UpdateException $e) { $data = $e->getData(); @@ -1379,6 +1387,7 @@ public function isAuthenticated(): bool { $updater->rollbackChanges($step); } http_response_code(500); + header('Content-Type: application/json'); echo(json_encode(['proceed' => false, 'response' => $data])); } catch (\Exception $e) { $message = $e->getMessage(); @@ -1394,6 +1403,7 @@ public function isAuthenticated(): bool { $updater->rollbackChanges($step); } http_response_code(500); + header('Content-Type: application/json'); echo(json_encode(['proceed' => false, 'response' => $message])); } diff --git a/lib/RecursiveDirectoryIteratorFilter.php b/lib/RecursiveDirectoryIteratorFilter.php new file mode 100644 index 00000000..15fbcd54 --- /dev/null +++ b/lib/RecursiveDirectoryIteratorFilter.php @@ -0,0 +1,26 @@ +excludedPaths = array_flip($excludedPaths); + } + + public function accept(): bool { + return !isset($this->excludedPaths[$this->current()->getFilename()]); + } +} diff --git a/lib/RecursiveDirectoryIteratorWithoutData.php b/lib/RecursiveDirectoryIteratorWithoutData.php deleted file mode 100644 index 3d9ddbdb..00000000 --- a/lib/RecursiveDirectoryIteratorWithoutData.php +++ /dev/null @@ -1,29 +0,0 @@ -current(); - if (!$current) { - return false; - } - - return !(in_array($current->getFilename(), $excludes, true) || $current->isDir()); - } -} diff --git a/lib/Updater.php b/lib/Updater.php index 031ba6f7..e3bf7f1e 100644 --- a/lib/Updater.php +++ b/lib/Updater.php @@ -10,7 +10,7 @@ namespace NC\Updater; class Updater { - private string $baseDir; + private string $nextcloudDir; private array $configValues = []; private string $currentVersion = 'unknown'; private string $buildTime; @@ -23,13 +23,15 @@ class Updater { * @param string $baseDir the absolute path to the /updater/ directory in the Nextcloud root * @throws \Exception */ - public function __construct(string $baseDir) { - $this->baseDir = $baseDir; + public function __construct( + private string $baseDir + ) { + $this->nextcloudDir = realpath(dirname($baseDir)); if ($dir = getenv('NEXTCLOUD_CONFIG_DIR')) { - $configFileName = rtrim($dir, '/') . '/config.php'; + $configFileName = realpath($dir . '/config.php'); } else { - $configFileName = $this->baseDir . '/../config/config.php'; + $configFileName = $this->nextcloudDir . '/config/config.php'; } if (!file_exists($configFileName)) { throw new \Exception('Could not find config.php. Is this file in the "updater" subfolder of Nextcloud?'); @@ -50,7 +52,7 @@ public function __construct(string $baseDir) { throw new \Exception('Could not read data directory from config.php.'); } - $versionFileName = $this->baseDir . '/../version.php'; + $versionFileName = $this->nextcloudDir . '/version.php'; if (!file_exists($versionFileName)) { // fallback to version in config.php $version = $this->getConfigOptionString('version'); @@ -81,19 +83,15 @@ public function __construct(string $baseDir) { /** * Returns whether the web updater is disabled - * - * @return bool */ - public function isDisabled() { + public function isDisabled(): bool { return $this->disabled; } /** * Returns current version or "unknown" if this could not be determined. - * - * @return string */ - public function getCurrentVersion() { + public function getCurrentVersion(): string { return $this->currentVersion; } @@ -101,7 +99,7 @@ public function getCurrentVersion() { * Returns currently used release channel */ private function getCurrentReleaseChannel(): string { - return ($this->getConfigOptionString('updater.release.channel') ?? 'stable'); + return $this->getConfigOptionString('updater.release.channel') ?? 'stable'; } /** @@ -273,16 +271,19 @@ private function getAppDirectories(): array { /** * Gets the recursive directory iterator over the Nextcloud folder * - * @return \RecursiveIteratorIterator<\RecursiveDirectoryIterator> + * @return \RecursiveIteratorIterator<\RecursiveDirectoryIterator|RecursiveDirectoryIteratorFilter> */ - private function getRecursiveDirectoryIterator(?string $folder = null): \RecursiveIteratorIterator { + private function getRecursiveDirectoryIterator(?string $folder = null, array $excludedPaths = []): \RecursiveIteratorIterator { if ($folder === null) { $folder = $this->baseDir . '/../'; } - return new \RecursiveIteratorIterator( - new \RecursiveDirectoryIterator($folder, \RecursiveDirectoryIterator::SKIP_DOTS), - \RecursiveIteratorIterator::CHILD_FIRST - ); + + $iterator = new \RecursiveDirectoryIterator($folder, \FilesystemIterator::SKIP_DOTS); + if (!empty($excludedPaths)) { + $iterator = new RecursiveDirectoryIteratorFilter($iterator, $excludedPaths); + } + + return new \RecursiveIteratorIterator($iterator, \RecursiveIteratorIterator::CHILD_FIRST); } /** @@ -293,7 +294,7 @@ public function checkForExpectedFilesAndFolders(): void { $expectedElements = $this->getExpectedElementsList(); $unexpectedElements = []; - foreach (new \DirectoryIterator($this->baseDir . '/../') as $fileInfo) { + foreach (new \DirectoryIterator($this->nextcloudDir) as $fileInfo) { if (array_search($fileInfo->getFilename(), $expectedElements) === false) { $unexpectedElements[] = $fileInfo->getFilename(); } @@ -311,15 +312,21 @@ public function checkForExpectedFilesAndFolders(): void { public function checkWritePermissions(): void { $this->silentLog('[info] checkWritePermissions()'); - $notWritablePaths = array(); - $dir = new \RecursiveDirectoryIterator($this->baseDir . '/../'); - $filter = new RecursiveDirectoryIteratorWithoutData($dir); - /** @var iterable */ - $it = new \RecursiveIteratorIterator($filter); + $excludedPaths = [ + '.rnd' => true, + '.well-known' => true, + 'data' => true, + ]; + + $it = new \DirectoryIterator($this->nextcloudDir); - foreach ($it as $path => $dir) { - if (!is_writable($path)) { - $notWritablePaths[] = $path; + $notWritablePaths = []; + foreach ($it as $path => $fileInfo) { + if ($fileInfo->isDot() || isset($excludedPaths[$fileInfo->getFilename()])) { + continue; + } + if (!$fileInfo->isWritable()) { + $notWritablePaths[] = $fileInfo->getFilename(); } } if (count($notWritablePaths) > 0) { @@ -392,7 +399,7 @@ public function createBackup(): void { * @var string $path * @var \SplFileInfo $fileInfo */ - foreach ($this->getRecursiveDirectoryIterator($currentDir) as $path => $fileInfo) { + foreach ($this->getRecursiveDirectoryIterator($currentDir, $excludedElements) as $path => $fileInfo) { $fileName = explode($currentDir, $path)[1]; $folderStructure = explode('/', $fileName, -1); @@ -921,8 +928,9 @@ public function deleteOldFiles(): void { } /** - * Moves the specified filed except the excluded elements to the correct position + * Moves the specified files except the excluded elements to the correct position * + * @param string[] $excludedElements * @throws \Exception */ private function moveWithExclusions(string $dataLocation, array $excludedElements): void { diff --git a/updater.phar b/updater.phar index ad43f18a03abb267e2803ec225373de29a40bf34..d340b35deb3bc4bfb079956d3111773eb2a0a54b 100755 GIT binary patch delta 8992 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 diff --git a/vendor/composer/autoload_classmap.php b/vendor/composer/autoload_classmap.php index 101e9c60..eaa5ad2f 100644 --- a/vendor/composer/autoload_classmap.php +++ b/vendor/composer/autoload_classmap.php @@ -24,7 +24,7 @@ 'JsonException' => $vendorDir . '/symfony/polyfill-php73/Resources/stubs/JsonException.php', 'NC\\Updater\\CommandApplication' => $baseDir . '/lib/CommandApplication.php', 'NC\\Updater\\LogException' => $baseDir . '/lib/LogException.php', - 'NC\\Updater\\RecursiveDirectoryIteratorWithoutData' => $baseDir . '/lib/RecursiveDirectoryIteratorWithoutData.php', + 'NC\\Updater\\RecursiveDirectoryIteratorFilter' => $baseDir . '/lib/RecursiveDirectoryIteratorFilter.php', 'NC\\Updater\\UpdateCommand' => $baseDir . '/lib/UpdateCommand.php', 'NC\\Updater\\UpdateException' => $baseDir . '/lib/UpdateException.php', 'NC\\Updater\\Updater' => $baseDir . '/lib/Updater.php', diff --git a/vendor/composer/autoload_static.php b/vendor/composer/autoload_static.php index 7cd88b34..b9d9d71a 100644 --- a/vendor/composer/autoload_static.php +++ b/vendor/composer/autoload_static.php @@ -119,7 +119,7 @@ class ComposerStaticInit936ba63ded5d1b8248cdb4d5673af0ea 'JsonException' => __DIR__ . '/..' . '/symfony/polyfill-php73/Resources/stubs/JsonException.php', 'NC\\Updater\\CommandApplication' => __DIR__ . '/../..' . '/lib/CommandApplication.php', 'NC\\Updater\\LogException' => __DIR__ . '/../..' . '/lib/LogException.php', - 'NC\\Updater\\RecursiveDirectoryIteratorWithoutData' => __DIR__ . '/../..' . '/lib/RecursiveDirectoryIteratorWithoutData.php', + 'NC\\Updater\\RecursiveDirectoryIteratorFilter' => __DIR__ . '/../..' . '/lib/RecursiveDirectoryIteratorFilter.php', 'NC\\Updater\\UpdateCommand' => __DIR__ . '/../..' . '/lib/UpdateCommand.php', 'NC\\Updater\\UpdateException' => __DIR__ . '/../..' . '/lib/UpdateException.php', 'NC\\Updater\\Updater' => __DIR__ . '/../..' . '/lib/Updater.php', From 044b838182405269ebfa7757195d8dfc62b4b578 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Tue, 4 Feb 2025 14:52:46 +0100 Subject: [PATCH 03/17] fix: Fix recursive iterating over files, avoid useless recursion in data folder MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- lib/Updater.php | 113 ++++++++++++++++-------------------------------- 1 file changed, 38 insertions(+), 75 deletions(-) diff --git a/lib/Updater.php b/lib/Updater.php index e3bf7f1e..c862dd3a 100644 --- a/lib/Updater.php +++ b/lib/Updater.php @@ -245,7 +245,7 @@ private function getExpectedElementsList(): array { /** * Returns app directories specified in config.php * - * @return list + * @return list Paths relative to nextcloud root directory */ private function getAppDirectories(): array { $expected = []; @@ -258,10 +258,12 @@ private function getAppDirectories(): array { if (!is_array($appsPath) || !isset($appsPath['path']) || !is_string($appsPath['path'])) { throw new \Exception('Invalid configuration in apps_paths configuration key'); } - $parentDir = realpath($this->baseDir . '/../'); $appDir = basename($appsPath['path']); - if (strpos($appsPath['path'], $parentDir) === 0 && $appDir !== 'apps') { - $expected[] = $appDir; + if (strpos($appsPath['path'], $this->nextcloudDir) === 0) { + $relativePath = substr($appsPath['path'], strlen($this->nextcloudDir)); + if ($relativePath !== 'apps') { + $expected[] = $relativePath; + } } } } @@ -271,19 +273,30 @@ private function getAppDirectories(): array { /** * Gets the recursive directory iterator over the Nextcloud folder * - * @return \RecursiveIteratorIterator<\RecursiveDirectoryIterator|RecursiveDirectoryIteratorFilter> + * @param list $excludedPaths Name of root directories to skip + * @return Generator */ - private function getRecursiveDirectoryIterator(?string $folder = null, array $excludedPaths = []): \RecursiveIteratorIterator { - if ($folder === null) { - $folder = $this->baseDir . '/../'; + private function getRecursiveDirectoryIterator(string $folder, array $excludedPaths): Generator { + foreach ($excludedElements as $element) { + if (strpos($element, '/') !== false) { + throw new \Exception('Excluding subpaths is not supported yet'); + } } - - $iterator = new \RecursiveDirectoryIterator($folder, \FilesystemIterator::SKIP_DOTS); - if (!empty($excludedPaths)) { - $iterator = new RecursiveDirectoryIteratorFilter($iterator, $excludedPaths); + $exclusions = array_flip($excludedPaths); + $handle = opendir($folder); + while ($name = readdir($handle)) { + if (in_array($name, ['.', '..'])) { + continue; + } + if (isset($exclusions[$name])) { + continue; + } + yield from $this->getRecursiveDirectoryIterator($folder.'/'.$name, []); } - return new \RecursiveIteratorIterator($iterator, \RecursiveIteratorIterator::CHILD_FIRST); + yield $folder => new SplFileInfo($folder); + + closedir($handle); } /** @@ -392,27 +405,8 @@ public function createBackup(): void { throw new \Exception('Could not create backup folder location'); } - // Copy the backup files - $currentDir = $this->baseDir . '/../'; - - /** - * @var string $path - * @var \SplFileInfo $fileInfo - */ - foreach ($this->getRecursiveDirectoryIterator($currentDir, $excludedElements) as $path => $fileInfo) { - $fileName = explode($currentDir, $path)[1]; - $folderStructure = explode('/', $fileName, -1); - - // Exclude the exclusions - if (isset($folderStructure[0])) { - if (array_search($folderStructure[0], $excludedElements) !== false) { - continue; - } - } else { - if (array_search($fileName, $excludedElements) !== false) { - continue; - } - } + foreach ($this->getRecursiveDirectoryIterator($this->nextcloudDir, $excludedElements) as $path => $fileInfo) { + $fileName = explode($this->nextcloudDir, $path)[1]; // Create folder if it doesn't exist if (!file_exists($backupFolderLocation . '/' . dirname($fileName))) { @@ -885,32 +879,14 @@ public function deleteOldFiles(): void { 'status.php', 'remote.php', 'public.php', - 'ocs/v1.php', - 'ocs/v2.php', + 'ocs', 'config', 'themes', 'apps', 'updater', ]; $excludedElements = array_merge($excludedElements, $this->getAppDirectories()); - /** - * @var string $path - * @var \SplFileInfo $fileInfo - */ - foreach ($this->getRecursiveDirectoryIterator() as $path => $fileInfo) { - $currentDir = $this->baseDir . '/../'; - $fileName = explode($currentDir, $path)[1]; - $folderStructure = explode('/', $fileName, -1); - // Exclude the exclusions - if (isset($folderStructure[0])) { - if (array_search($folderStructure[0], $excludedElements) !== false) { - continue; - } - } else { - if (array_search($fileName, $excludedElements) !== false) { - continue; - } - } + foreach ($this->getRecursiveDirectoryIterator($this->nextcloudDir, $excludedElements) as $path => $fileInfo) { if ($fileInfo->isFile() || $fileInfo->isLink()) { $state = unlink($path); if ($state === false) { @@ -930,28 +906,12 @@ public function deleteOldFiles(): void { /** * Moves the specified files except the excluded elements to the correct position * - * @param string[] $excludedElements + * @param list $excludedPaths Name of root directories to skip * @throws \Exception */ private function moveWithExclusions(string $dataLocation, array $excludedElements): void { - /** - * @var string $path - * @var \SplFileInfo $fileInfo - */ - foreach ($this->getRecursiveDirectoryIterator($dataLocation) as $path => $fileInfo) { + foreach ($this->getRecursiveDirectoryIterator($dataLocation, $excludedElements) as $path => $fileInfo) { $fileName = explode($dataLocation, $path)[1]; - $folderStructure = explode('/', $fileName, -1); - - // Exclude the exclusions - if (isset($folderStructure[0])) { - if (array_search($folderStructure[0], $excludedElements) !== false) { - continue; - } - } else { - if (array_search($fileName, $excludedElements) !== false) { - continue; - } - } if ($fileInfo->isFile()) { if (!file_exists($this->baseDir . '/../' . dirname($fileName))) { @@ -995,16 +955,19 @@ public function moveNewVersionInPlace(): void { 'status.php', 'remote.php', 'public.php', - 'ocs/v1.php', - 'ocs/v2.php', + 'ocs', ]; $storageLocation = $this->getUpdateDirectoryLocation() . '/updater-'.$this->getConfigOptionMandatoryString('instanceid') . '/downloads/nextcloud/'; $this->silentLog('[info] storage location: ' . $storageLocation); + + // Rename apps and other stuff $this->moveWithExclusions($storageLocation, $excludedElements); - // Rename everything except the updater files + // Rename everything except the updater (It will not move what was already moved as it’s not in $storageLocation anymore) $this->moveWithExclusions($storageLocation, ['updater']); + // The updater folder is moved last in finalize() + $this->silentLog('[info] end of moveNewVersionInPlace()'); } From b2372ea7c7e02670576e0f39a82d9cf6bfde4c13 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Tue, 4 Feb 2025 15:08:51 +0100 Subject: [PATCH 04/17] fix: Use the new Generator in more places and avoid yielding root folder MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- lib/Updater.php | 40 ++++++++++++---------------------------- 1 file changed, 12 insertions(+), 28 deletions(-) diff --git a/lib/Updater.php b/lib/Updater.php index c862dd3a..a45a350f 100644 --- a/lib/Updater.php +++ b/lib/Updater.php @@ -291,10 +291,11 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa if (isset($exclusions[$name])) { continue; } - yield from $this->getRecursiveDirectoryIterator($folder.'/'.$name, []); + $path = $folder.'/'.$name; + yield from $this->getRecursiveDirectoryIterator($path, []); + yield $path => new SplFileInfo($path); } - yield $folder => new SplFileInfo($folder); closedir($handle); } @@ -325,19 +326,14 @@ public function checkForExpectedFilesAndFolders(): void { public function checkWritePermissions(): void { $this->silentLog('[info] checkWritePermissions()'); - $excludedPaths = [ - '.rnd' => true, - '.well-known' => true, - 'data' => true, + $excludedElements = [ + '.rnd', + '.well-known', + 'data', ]; - $it = new \DirectoryIterator($this->nextcloudDir); - $notWritablePaths = []; - foreach ($it as $path => $fileInfo) { - if ($fileInfo->isDot() || isset($excludedPaths[$fileInfo->getFilename()])) { - continue; - } + foreach ($this->getRecursiveDirectoryIterator($this->nextcloudDir, $excludedElements) as $path => $fileInfo) { if (!$fileInfo->isWritable()) { $notWritablePaths[] = $fileInfo->getFilename(); } @@ -778,33 +774,21 @@ private function recursiveDelete(string $folder): void { if (!file_exists($folder)) { return; } - /** @var iterable<\SplFileInfo> $iterator */ - $iterator = new \RecursiveIteratorIterator( - new \RecursiveDirectoryIterator($folder, \RecursiveDirectoryIterator::SKIP_DOTS), - \RecursiveIteratorIterator::CHILD_FIRST - ); $directories = []; $files = []; - foreach ($iterator as $fileInfo) { + foreach ($this->getRecursiveDirectoryIterator($folder, []) as $fileInfo) { if ($fileInfo->isDir()) { - $directories[] = $fileInfo->getRealPath(); + rmdir($fileInfo->getRealPath()); } else { if ($fileInfo->isLink()) { - $files[] = $fileInfo->getPathName(); + unlink($fileInfo->getPathName()); } else { - $files[] = $fileInfo->getRealPath(); + unlink($fileInfo->getRealPath()); } } } - foreach ($files as $file) { - unlink($file); - } - foreach ($directories as $dir) { - rmdir($dir); - } - $state = rmdir($folder); if ($state === false) { throw new \Exception('Could not rmdir ' . $folder); From 5abf17deb41b27fd291cb4cbf73db0575b1b8a1e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Tue, 4 Feb 2025 15:12:55 +0100 Subject: [PATCH 05/17] fix: Remove now unused class and generate index.php and phar MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- Makefile | 4 +- index.php | 166 +++++++---------------- lib/RecursiveDirectoryIteratorFilter.php | 26 ---- updater.phar | Bin 1169341 -> 1167214 bytes vendor/composer/autoload_classmap.php | 1 - vendor/composer/autoload_static.php | 1 - 6 files changed, 50 insertions(+), 148 deletions(-) delete mode 100644 lib/RecursiveDirectoryIteratorFilter.php diff --git a/Makefile b/Makefile index 0ef93338..23025848 100644 --- a/Makefile +++ b/Makefile @@ -12,11 +12,11 @@ updater.phar: updater.php lib/*.php buildVersionFile.php clean: rm updater.phar index.php -index.php: lib/UpdateException.php lib/LogException.php lib/RecursiveDirectoryIteratorFilter.php lib/Updater.php index.web.php +index.php: lib/UpdateException.php lib/LogException.php lib/Updater.php index.web.php # First put openining php tag and license awk '/^<\?php$$/,/\*\//' index.web.php > index.php # Then concat all files while filtering php tag and license - cat lib/UpdateException.php lib/LogException.php lib/RecursiveDirectoryIteratorFilter.php lib/Updater.php index.web.php| grep -v "^namespace" | awk '/^<\?php$$/,/\*\//{next} 1' >> index.php + cat lib/UpdateException.php lib/LogException.php lib/Updater.php index.web.php| grep -v "^namespace" | awk '/^<\?php$$/,/\*\//{next} 1' >> index.php test/vendor: cd tests && composer install diff --git a/index.php b/index.php index 9bd69f12..0dd624a5 100644 --- a/index.php +++ b/index.php @@ -27,23 +27,6 @@ class LogException extends \Exception { } -class RecursiveDirectoryIteratorFilter extends \RecursiveFilterIterator { - private array $excludedPaths; - - public function __construct( - \RecursiveDirectoryIterator $iterator, - array $excludedPaths = ['data'], - ) { - parent::__construct($iterator); - $this->excludedPaths = array_flip($excludedPaths); - } - - public function accept(): bool { - return !isset($this->excludedPaths[$this->current()->getFilename()]); - } -} - - class Updater { private string $nextcloudDir; private array $configValues = []; @@ -280,7 +263,7 @@ private function getExpectedElementsList(): array { /** * Returns app directories specified in config.php * - * @return list + * @return list Paths relative to nextcloud root directory */ private function getAppDirectories(): array { $expected = []; @@ -293,10 +276,12 @@ private function getAppDirectories(): array { if (!is_array($appsPath) || !isset($appsPath['path']) || !is_string($appsPath['path'])) { throw new \Exception('Invalid configuration in apps_paths configuration key'); } - $parentDir = realpath($this->baseDir . '/../'); $appDir = basename($appsPath['path']); - if (strpos($appsPath['path'], $parentDir) === 0 && $appDir !== 'apps') { - $expected[] = $appDir; + if (strpos($appsPath['path'], $this->nextcloudDir) === 0) { + $relativePath = substr($appsPath['path'], strlen($this->nextcloudDir)); + if ($relativePath !== 'apps') { + $expected[] = $relativePath; + } } } } @@ -306,19 +291,31 @@ private function getAppDirectories(): array { /** * Gets the recursive directory iterator over the Nextcloud folder * - * @return \RecursiveIteratorIterator<\RecursiveDirectoryIterator|RecursiveDirectoryIteratorFilter> + * @param list $excludedPaths Name of root directories to skip + * @return Generator */ - private function getRecursiveDirectoryIterator(?string $folder = null, array $excludedPaths = []): \RecursiveIteratorIterator { - if ($folder === null) { - $folder = $this->baseDir . '/../'; + private function getRecursiveDirectoryIterator(string $folder, array $excludedPaths): Generator { + foreach ($excludedElements as $element) { + if (strpos($element, '/') !== false) { + throw new \Exception('Excluding subpaths is not supported yet'); + } } - - $iterator = new \RecursiveDirectoryIterator($folder, \FilesystemIterator::SKIP_DOTS); - if (!empty($excludedPaths)) { - $iterator = new RecursiveDirectoryIteratorFilter($iterator, $excludedPaths); + $exclusions = array_flip($excludedPaths); + $handle = opendir($folder); + while ($name = readdir($handle)) { + if (in_array($name, ['.', '..'])) { + continue; + } + if (isset($exclusions[$name])) { + continue; + } + $path = $folder.'/'.$name; + yield from $this->getRecursiveDirectoryIterator($path, []); + yield $path => new SplFileInfo($path); } - return new \RecursiveIteratorIterator($iterator, \RecursiveIteratorIterator::CHILD_FIRST); + + closedir($handle); } /** @@ -347,19 +344,14 @@ public function checkForExpectedFilesAndFolders(): void { public function checkWritePermissions(): void { $this->silentLog('[info] checkWritePermissions()'); - $excludedPaths = [ - '.rnd' => true, - '.well-known' => true, - 'data' => true, + $excludedElements = [ + '.rnd', + '.well-known', + 'data', ]; - $it = new \DirectoryIterator($this->nextcloudDir); - $notWritablePaths = []; - foreach ($it as $path => $fileInfo) { - if ($fileInfo->isDot() || isset($excludedPaths[$fileInfo->getFilename()])) { - continue; - } + foreach ($this->getRecursiveDirectoryIterator($this->nextcloudDir, $excludedElements) as $path => $fileInfo) { if (!$fileInfo->isWritable()) { $notWritablePaths[] = $fileInfo->getFilename(); } @@ -427,27 +419,8 @@ public function createBackup(): void { throw new \Exception('Could not create backup folder location'); } - // Copy the backup files - $currentDir = $this->baseDir . '/../'; - - /** - * @var string $path - * @var \SplFileInfo $fileInfo - */ - foreach ($this->getRecursiveDirectoryIterator($currentDir, $excludedElements) as $path => $fileInfo) { - $fileName = explode($currentDir, $path)[1]; - $folderStructure = explode('/', $fileName, -1); - - // Exclude the exclusions - if (isset($folderStructure[0])) { - if (array_search($folderStructure[0], $excludedElements) !== false) { - continue; - } - } else { - if (array_search($fileName, $excludedElements) !== false) { - continue; - } - } + foreach ($this->getRecursiveDirectoryIterator($this->nextcloudDir, $excludedElements) as $path => $fileInfo) { + $fileName = explode($this->nextcloudDir, $path)[1]; // Create folder if it doesn't exist if (!file_exists($backupFolderLocation . '/' . dirname($fileName))) { @@ -819,33 +792,21 @@ private function recursiveDelete(string $folder): void { if (!file_exists($folder)) { return; } - /** @var iterable<\SplFileInfo> $iterator */ - $iterator = new \RecursiveIteratorIterator( - new \RecursiveDirectoryIterator($folder, \RecursiveDirectoryIterator::SKIP_DOTS), - \RecursiveIteratorIterator::CHILD_FIRST - ); $directories = []; $files = []; - foreach ($iterator as $fileInfo) { + foreach ($this->getRecursiveDirectoryIterator($folder, []) as $fileInfo) { if ($fileInfo->isDir()) { - $directories[] = $fileInfo->getRealPath(); + rmdir($fileInfo->getRealPath()); } else { if ($fileInfo->isLink()) { - $files[] = $fileInfo->getPathName(); + unlink($fileInfo->getPathName()); } else { - $files[] = $fileInfo->getRealPath(); + unlink($fileInfo->getRealPath()); } } } - foreach ($files as $file) { - unlink($file); - } - foreach ($directories as $dir) { - rmdir($dir); - } - $state = rmdir($folder); if ($state === false) { throw new \Exception('Could not rmdir ' . $folder); @@ -920,32 +881,14 @@ public function deleteOldFiles(): void { 'status.php', 'remote.php', 'public.php', - 'ocs/v1.php', - 'ocs/v2.php', + 'ocs', 'config', 'themes', 'apps', 'updater', ]; $excludedElements = array_merge($excludedElements, $this->getAppDirectories()); - /** - * @var string $path - * @var \SplFileInfo $fileInfo - */ - foreach ($this->getRecursiveDirectoryIterator() as $path => $fileInfo) { - $currentDir = $this->baseDir . '/../'; - $fileName = explode($currentDir, $path)[1]; - $folderStructure = explode('/', $fileName, -1); - // Exclude the exclusions - if (isset($folderStructure[0])) { - if (array_search($folderStructure[0], $excludedElements) !== false) { - continue; - } - } else { - if (array_search($fileName, $excludedElements) !== false) { - continue; - } - } + foreach ($this->getRecursiveDirectoryIterator($this->nextcloudDir, $excludedElements) as $path => $fileInfo) { if ($fileInfo->isFile() || $fileInfo->isLink()) { $state = unlink($path); if ($state === false) { @@ -965,28 +908,12 @@ public function deleteOldFiles(): void { /** * Moves the specified files except the excluded elements to the correct position * - * @param string[] $excludedElements + * @param list $excludedPaths Name of root directories to skip * @throws \Exception */ private function moveWithExclusions(string $dataLocation, array $excludedElements): void { - /** - * @var string $path - * @var \SplFileInfo $fileInfo - */ - foreach ($this->getRecursiveDirectoryIterator($dataLocation) as $path => $fileInfo) { + foreach ($this->getRecursiveDirectoryIterator($dataLocation, $excludedElements) as $path => $fileInfo) { $fileName = explode($dataLocation, $path)[1]; - $folderStructure = explode('/', $fileName, -1); - - // Exclude the exclusions - if (isset($folderStructure[0])) { - if (array_search($folderStructure[0], $excludedElements) !== false) { - continue; - } - } else { - if (array_search($fileName, $excludedElements) !== false) { - continue; - } - } if ($fileInfo->isFile()) { if (!file_exists($this->baseDir . '/../' . dirname($fileName))) { @@ -1030,16 +957,19 @@ public function moveNewVersionInPlace(): void { 'status.php', 'remote.php', 'public.php', - 'ocs/v1.php', - 'ocs/v2.php', + 'ocs', ]; $storageLocation = $this->getUpdateDirectoryLocation() . '/updater-'.$this->getConfigOptionMandatoryString('instanceid') . '/downloads/nextcloud/'; $this->silentLog('[info] storage location: ' . $storageLocation); + + // Rename apps and other stuff $this->moveWithExclusions($storageLocation, $excludedElements); - // Rename everything except the updater files + // Rename everything except the updater (It will not move what was already moved as it’s not in $storageLocation anymore) $this->moveWithExclusions($storageLocation, ['updater']); + // The updater folder is moved last in finalize() + $this->silentLog('[info] end of moveNewVersionInPlace()'); } diff --git a/lib/RecursiveDirectoryIteratorFilter.php b/lib/RecursiveDirectoryIteratorFilter.php deleted file mode 100644 index 15fbcd54..00000000 --- a/lib/RecursiveDirectoryIteratorFilter.php +++ /dev/null @@ -1,26 +0,0 @@ -excludedPaths = array_flip($excludedPaths); - } - - public function accept(): bool { - return !isset($this->excludedPaths[$this->current()->getFilename()]); - } -} diff --git a/updater.phar b/updater.phar index d340b35deb3bc4bfb079956d3111773eb2a0a54b..30f36c88ab19dfc39f74a7eca2efd23f873b1e1e 100755 GIT binary patch delta 1757 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 LjsD=)N4NeC2d4n} diff --git a/vendor/composer/autoload_classmap.php b/vendor/composer/autoload_classmap.php index eaa5ad2f..9e980904 100644 --- a/vendor/composer/autoload_classmap.php +++ b/vendor/composer/autoload_classmap.php @@ -24,7 +24,6 @@ 'JsonException' => $vendorDir . '/symfony/polyfill-php73/Resources/stubs/JsonException.php', 'NC\\Updater\\CommandApplication' => $baseDir . '/lib/CommandApplication.php', 'NC\\Updater\\LogException' => $baseDir . '/lib/LogException.php', - 'NC\\Updater\\RecursiveDirectoryIteratorFilter' => $baseDir . '/lib/RecursiveDirectoryIteratorFilter.php', 'NC\\Updater\\UpdateCommand' => $baseDir . '/lib/UpdateCommand.php', 'NC\\Updater\\UpdateException' => $baseDir . '/lib/UpdateException.php', 'NC\\Updater\\Updater' => $baseDir . '/lib/Updater.php', diff --git a/vendor/composer/autoload_static.php b/vendor/composer/autoload_static.php index b9d9d71a..0a268bc1 100644 --- a/vendor/composer/autoload_static.php +++ b/vendor/composer/autoload_static.php @@ -119,7 +119,6 @@ class ComposerStaticInit936ba63ded5d1b8248cdb4d5673af0ea 'JsonException' => __DIR__ . '/..' . '/symfony/polyfill-php73/Resources/stubs/JsonException.php', 'NC\\Updater\\CommandApplication' => __DIR__ . '/../..' . '/lib/CommandApplication.php', 'NC\\Updater\\LogException' => __DIR__ . '/../..' . '/lib/LogException.php', - 'NC\\Updater\\RecursiveDirectoryIteratorFilter' => __DIR__ . '/../..' . '/lib/RecursiveDirectoryIteratorFilter.php', 'NC\\Updater\\UpdateCommand' => __DIR__ . '/../..' . '/lib/UpdateCommand.php', 'NC\\Updater\\UpdateException' => __DIR__ . '/../..' . '/lib/UpdateException.php', 'NC\\Updater\\Updater' => __DIR__ . '/../..' . '/lib/Updater.php', From f869f0602e9eef957c9d26824b138438bf3a88ea Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Tue, 4 Feb 2025 15:17:20 +0100 Subject: [PATCH 06/17] fix: Fix namespaces and typo in variable names MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- index.php | 10 +++++----- lib/Updater.php | 10 +++++----- updater.phar | Bin 1167214 -> 1167217 bytes 3 files changed, 10 insertions(+), 10 deletions(-) diff --git a/index.php b/index.php index 0dd624a5..e8e8f6c3 100644 --- a/index.php +++ b/index.php @@ -292,10 +292,10 @@ private function getAppDirectories(): array { * Gets the recursive directory iterator over the Nextcloud folder * * @param list $excludedPaths Name of root directories to skip - * @return Generator + * @return \Generator */ - private function getRecursiveDirectoryIterator(string $folder, array $excludedPaths): Generator { - foreach ($excludedElements as $element) { + private function getRecursiveDirectoryIterator(string $folder, array $excludedPaths): \Generator { + foreach ($excludedPaths as $element) { if (strpos($element, '/') !== false) { throw new \Exception('Excluding subpaths is not supported yet'); } @@ -311,7 +311,7 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa } $path = $folder.'/'.$name; yield from $this->getRecursiveDirectoryIterator($path, []); - yield $path => new SplFileInfo($path); + yield $path => new \SplFileInfo($path); } @@ -908,7 +908,7 @@ public function deleteOldFiles(): void { /** * Moves the specified files except the excluded elements to the correct position * - * @param list $excludedPaths Name of root directories to skip + * @param list $excludedElements Name of root directories to skip * @throws \Exception */ private function moveWithExclusions(string $dataLocation, array $excludedElements): void { diff --git a/lib/Updater.php b/lib/Updater.php index a45a350f..02fc3a4b 100644 --- a/lib/Updater.php +++ b/lib/Updater.php @@ -274,10 +274,10 @@ private function getAppDirectories(): array { * Gets the recursive directory iterator over the Nextcloud folder * * @param list $excludedPaths Name of root directories to skip - * @return Generator + * @return \Generator */ - private function getRecursiveDirectoryIterator(string $folder, array $excludedPaths): Generator { - foreach ($excludedElements as $element) { + private function getRecursiveDirectoryIterator(string $folder, array $excludedPaths): \Generator { + foreach ($excludedPaths as $element) { if (strpos($element, '/') !== false) { throw new \Exception('Excluding subpaths is not supported yet'); } @@ -293,7 +293,7 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa } $path = $folder.'/'.$name; yield from $this->getRecursiveDirectoryIterator($path, []); - yield $path => new SplFileInfo($path); + yield $path => new \SplFileInfo($path); } @@ -890,7 +890,7 @@ public function deleteOldFiles(): void { /** * Moves the specified files except the excluded elements to the correct position * - * @param list $excludedPaths Name of root directories to skip + * @param list $excludedElements Name of root directories to skip * @throws \Exception */ private function moveWithExclusions(string $dataLocation, array $excludedElements): void { diff --git a/updater.phar b/updater.phar index 30f36c88ab19dfc39f74a7eca2efd23f873b1e1e..a2d849d7fd5daf3efa5abcbb431d03a6fc5c3e16 100755 GIT binary patch delta 258 zcmaDi&;8>(_X+cP5|fis(@f2ij7?08CayL{<-ZC-;cxa}Y_(1i@q5U0DSKWFfzt$7f}=Z=gsb#lbV~FSF&BKNYEx$M*7#AH$N?k_#Uh>UpX&lcZ!VJHa{ky Jo86s!odDpLQ5OIJ delta 272 zcmex3&;8vz_X+cPk}T8G%u|e0&CCsxCayL{<-ZC-;cxa}Y_()5yJ*fRn#6A&{4F$)m00x=s9vjZ^)5OV@C7Z7s;F%J;)0x=&D^KaL& z7jQbtWulv&WMph^l$yA`f<;hPe)=?J!5Ve<)V$Q9#FG3Xg=#KN&b0iZ)WqZr1r3$d zisYQql++a0oYdUZyprwaDuQ Date: Tue, 4 Feb 2025 15:42:36 +0100 Subject: [PATCH 07/17] chore: Update updater.phar MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- updater.phar | Bin 1167217 -> 1167217 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/updater.phar b/updater.phar index a2d849d7fd5daf3efa5abcbb431d03a6fc5c3e16..4ed911a8181e0c5cc2306aef133564d074471927 100755 GIT binary patch delta 175 zcmex3&;8>(_X+cPOcD(&OpFaIEi6qfCayL{<-ZC-;cxa}Y_(+(*rm9#`J!F>MLR|y zW&&bnAZ7t#Rv=~rVs;?r0Afxc<^p1FAm#yLULfWJV*c$H?F1GaWlys(vrIEE+g`yU lc=wcy<}E|HxhV!bZ>K0!i8YFL96ak_#>BwD;O^w>1OQKDK7{}P delta 175 zcmex3&;8>(_X+cP5|fis(@f2ij7?08CayL{<-ZC-;cxa}Y_(rFA(zqG5_|9b^;5IvKyzEC7YWYY_DJu lyn9MU`q!H`KP`&*9;`B7IWK2-ij3JdKPCnS26rc4Cji!5Lp=Zh From 5b27f07c8fadc69697d19b83b72f93187b80c295 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Tue, 4 Feb 2025 15:47:58 +0100 Subject: [PATCH 08/17] fix: Only recurse on directories MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- lib/Updater.php | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/lib/Updater.php b/lib/Updater.php index 02fc3a4b..2fb49da9 100644 --- a/lib/Updater.php +++ b/lib/Updater.php @@ -283,7 +283,12 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa } } $exclusions = array_flip($excludedPaths); + $handle = opendir($folder); + + if ($handle === false) { + throw new \Exception('Could not open '.$folder); + } while ($name = readdir($handle)) { if (in_array($name, ['.', '..'])) { continue; @@ -292,7 +297,9 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa continue; } $path = $folder.'/'.$name; - yield from $this->getRecursiveDirectoryIterator($path, []); + if (is_dir($path)) { + yield from $this->getRecursiveDirectoryIterator($path, []); + } yield $path => new \SplFileInfo($path); } From c504bf596664d9b1fb3f4142da00084a05e93e0d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Tue, 4 Feb 2025 15:48:18 +0100 Subject: [PATCH 09/17] chore: make index.php updater.phar MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- index.php | 9 ++++++++- updater.phar | Bin 1167217 -> 1167332 bytes 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/index.php b/index.php index e8e8f6c3..302cbd49 100644 --- a/index.php +++ b/index.php @@ -301,7 +301,12 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa } } $exclusions = array_flip($excludedPaths); + $handle = opendir($folder); + + if ($handle === false) { + throw new \Exception('Could not open '.$folder); + } while ($name = readdir($handle)) { if (in_array($name, ['.', '..'])) { continue; @@ -310,7 +315,9 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa continue; } $path = $folder.'/'.$name; - yield from $this->getRecursiveDirectoryIterator($path, []); + if (is_dir($path)) { + yield from $this->getRecursiveDirectoryIterator($path, []); + } yield $path => new \SplFileInfo($path); } diff --git a/updater.phar b/updater.phar index 4ed911a8181e0c5cc2306aef133564d074471927..09762c27b0e24adb70fa0641f20ee39432e1b462 100755 GIT binary patch delta 285 zcmex3&;7}K_X+cPj15x_OpPoIQZ14UC$2U|<-ZC-;cxa}Y_(9rh<@NN^4k^97*_&4}0lnkyK0!i8YFL96ak_#sqYYyOXaI07)`H^Z)<= From a81b79af7ff9ff09aa2769033055012b2227b48b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Tue, 4 Feb 2025 15:51:20 +0100 Subject: [PATCH 10/17] chore: composer install MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- vendor/composer/InstalledVersions.php | 27 ++++++++++++++--- vendor/composer/autoload_classmap.php | 1 - vendor/composer/autoload_static.php | 1 - vendor/composer/installed.json | 28 +++++++++--------- vendor/composer/installed.php | 18 +++++------ vendor/nextcloud/coding-standard/CHANGELOG.md | 27 +++++++++++++++++ vendor/nextcloud/coding-standard/README.md | 2 +- .../nextcloud/coding-standard/src/Config.php | 5 ++++ vendor/php-cs-fixer/shim/logo.md | 2 +- vendor/php-cs-fixer/shim/php-cs-fixer.phar | Bin 2723318 -> 2839217 bytes .../php-cs-fixer/shim/php-cs-fixer.phar.asc | Bin 566 -> 566 bytes 11 files changed, 80 insertions(+), 31 deletions(-) diff --git a/vendor/composer/InstalledVersions.php b/vendor/composer/InstalledVersions.php index 51e734a7..6d29bff6 100644 --- a/vendor/composer/InstalledVersions.php +++ b/vendor/composer/InstalledVersions.php @@ -32,6 +32,11 @@ class InstalledVersions */ private static $installed; + /** + * @var bool + */ + private static $installedIsLocalDir; + /** * @var bool|null */ @@ -309,6 +314,12 @@ public static function reload($data) { self::$installed = $data; self::$installedByVendor = array(); + + // when using reload, we disable the duplicate protection to ensure that self::$installed data is + // always returned, but we cannot know whether it comes from the installed.php in __DIR__ or not, + // so we have to assume it does not, and that may result in duplicate data being returned when listing + // all installed packages for example + self::$installedIsLocalDir = false; } /** @@ -322,19 +333,27 @@ private static function getInstalled() } $installed = array(); + $copiedLocalDir = false; if (self::$canGetVendors) { + $selfDir = strtr(__DIR__, '\\', '/'); foreach (ClassLoader::getRegisteredLoaders() as $vendorDir => $loader) { + $vendorDir = strtr($vendorDir, '\\', '/'); if (isset(self::$installedByVendor[$vendorDir])) { $installed[] = self::$installedByVendor[$vendorDir]; } elseif (is_file($vendorDir.'/composer/installed.php')) { /** @var array{root: array{name: string, pretty_version: string, version: string, reference: string|null, type: string, install_path: string, aliases: string[], dev: bool}, versions: array} $required */ $required = require $vendorDir.'/composer/installed.php'; - $installed[] = self::$installedByVendor[$vendorDir] = $required; - if (null === self::$installed && strtr($vendorDir.'/composer', '\\', '/') === strtr(__DIR__, '\\', '/')) { - self::$installed = $installed[count($installed) - 1]; + self::$installedByVendor[$vendorDir] = $required; + $installed[] = $required; + if (self::$installed === null && $vendorDir.'/composer' === $selfDir) { + self::$installed = $required; + self::$installedIsLocalDir = true; } } + if (self::$installedIsLocalDir && $vendorDir.'/composer' === $selfDir) { + $copiedLocalDir = true; + } } } @@ -350,7 +369,7 @@ private static function getInstalled() } } - if (self::$installed !== array()) { + if (self::$installed !== array() && !$copiedLocalDir) { $installed[] = self::$installed; } diff --git a/vendor/composer/autoload_classmap.php b/vendor/composer/autoload_classmap.php index 9e980904..3302d88e 100644 --- a/vendor/composer/autoload_classmap.php +++ b/vendor/composer/autoload_classmap.php @@ -27,7 +27,6 @@ 'NC\\Updater\\UpdateCommand' => $baseDir . '/lib/UpdateCommand.php', 'NC\\Updater\\UpdateException' => $baseDir . '/lib/UpdateException.php', 'NC\\Updater\\Updater' => $baseDir . '/lib/Updater.php', - 'NC\\Updater\\Version' => $baseDir . '/lib/Version.php', 'Nextcloud\\CodingStandard\\Config' => $vendorDir . '/nextcloud/coding-standard/src/Config.php', 'Normalizer' => $vendorDir . '/symfony/polyfill-intl-normalizer/Resources/stubs/Normalizer.php', 'PhpToken' => $vendorDir . '/symfony/polyfill-php80/Resources/stubs/PhpToken.php', diff --git a/vendor/composer/autoload_static.php b/vendor/composer/autoload_static.php index 0a268bc1..3e2e9de5 100644 --- a/vendor/composer/autoload_static.php +++ b/vendor/composer/autoload_static.php @@ -122,7 +122,6 @@ class ComposerStaticInit936ba63ded5d1b8248cdb4d5673af0ea 'NC\\Updater\\UpdateCommand' => __DIR__ . '/../..' . '/lib/UpdateCommand.php', 'NC\\Updater\\UpdateException' => __DIR__ . '/../..' . '/lib/UpdateException.php', 'NC\\Updater\\Updater' => __DIR__ . '/../..' . '/lib/Updater.php', - 'NC\\Updater\\Version' => __DIR__ . '/../..' . '/lib/Version.php', 'Nextcloud\\CodingStandard\\Config' => __DIR__ . '/..' . '/nextcloud/coding-standard/src/Config.php', 'Normalizer' => __DIR__ . '/..' . '/symfony/polyfill-intl-normalizer/Resources/stubs/Normalizer.php', 'PhpToken' => __DIR__ . '/..' . '/symfony/polyfill-php80/Resources/stubs/PhpToken.php', diff --git a/vendor/composer/installed.json b/vendor/composer/installed.json index a2bab66c..12dbac5a 100644 --- a/vendor/composer/installed.json +++ b/vendor/composer/installed.json @@ -62,24 +62,24 @@ }, { "name": "nextcloud/coding-standard", - "version": "v1.1.1", - "version_normalized": "1.1.1.0", + "version": "v1.2.1", + "version_normalized": "1.2.1.0", "source": { "type": "git", "url": "https://github.com/nextcloud/coding-standard.git", - "reference": "55def702fb9a37a219511e1d8c6fe8e37164c1fb" + "reference": "cf5f18d989ec62fb4cdc7fc92a36baf34b3d829e" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nextcloud/coding-standard/zipball/55def702fb9a37a219511e1d8c6fe8e37164c1fb", - "reference": "55def702fb9a37a219511e1d8c6fe8e37164c1fb", + "url": "https://api.github.com/repos/nextcloud/coding-standard/zipball/cf5f18d989ec62fb4cdc7fc92a36baf34b3d829e", + "reference": "cf5f18d989ec62fb4cdc7fc92a36baf34b3d829e", "shasum": "" }, "require": { "php": "^7.3|^8.0", "php-cs-fixer/shim": "^3.17" }, - "time": "2023-06-01T12:05:01+00:00", + "time": "2024-02-01T14:54:37+00:00", "type": "library", "installation-source": "dist", "autoload": { @@ -100,23 +100,23 @@ "description": "Nextcloud coding standards for the php cs fixer", "support": { "issues": "https://github.com/nextcloud/coding-standard/issues", - "source": "https://github.com/nextcloud/coding-standard/tree/v1.1.1" + "source": "https://github.com/nextcloud/coding-standard/tree/v1.2.1" }, "install-path": "../nextcloud/coding-standard" }, { "name": "php-cs-fixer/shim", - "version": "v3.17.0", - "version_normalized": "3.17.0.0", + "version": "v3.51.0", + "version_normalized": "3.51.0.0", "source": { "type": "git", "url": "https://github.com/PHP-CS-Fixer/shim.git", - "reference": "f51b4aed90565c447136f1d015798f6f7c82490f" + "reference": "a792394f7f3934f75a4df9dca544796c6f503027" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/PHP-CS-Fixer/shim/zipball/f51b4aed90565c447136f1d015798f6f7c82490f", - "reference": "f51b4aed90565c447136f1d015798f6f7c82490f", + "url": "https://api.github.com/repos/PHP-CS-Fixer/shim/zipball/a792394f7f3934f75a4df9dca544796c6f503027", + "reference": "a792394f7f3934f75a4df9dca544796c6f503027", "shasum": "" }, "require": { @@ -131,7 +131,7 @@ "ext-dom": "For handling output formats in XML", "ext-mbstring": "For handling non-UTF8 characters." }, - "time": "2023-05-22T20:00:38+00:00", + "time": "2024-02-28T19:51:07+00:00", "bin": [ "php-cs-fixer", "php-cs-fixer.phar" @@ -155,7 +155,7 @@ "description": "A tool to automatically fix PHP code style", "support": { "issues": "https://github.com/PHP-CS-Fixer/shim/issues", - "source": "https://github.com/PHP-CS-Fixer/shim/tree/v3.17.0" + "source": "https://github.com/PHP-CS-Fixer/shim/tree/v3.51.0" }, "install-path": "../php-cs-fixer/shim" }, diff --git a/vendor/composer/installed.php b/vendor/composer/installed.php index 6aecd5e3..c68e281a 100644 --- a/vendor/composer/installed.php +++ b/vendor/composer/installed.php @@ -3,7 +3,7 @@ 'name' => '__root__', 'pretty_version' => 'dev-master', 'version' => 'dev-master', - 'reference' => 'de0582d00a183fca1d5645d354e88b94b9b75a90', + 'reference' => 'c504bf596664d9b1fb3f4142da00084a05e93e0d', 'type' => 'library', 'install_path' => __DIR__ . '/../../', 'aliases' => array(), @@ -13,7 +13,7 @@ '__root__' => array( 'pretty_version' => 'dev-master', 'version' => 'dev-master', - 'reference' => 'de0582d00a183fca1d5645d354e88b94b9b75a90', + 'reference' => 'c504bf596664d9b1fb3f4142da00084a05e93e0d', 'type' => 'library', 'install_path' => __DIR__ . '/../../', 'aliases' => array(), @@ -31,22 +31,22 @@ 'friendsofphp/php-cs-fixer' => array( 'dev_requirement' => true, 'replaced' => array( - 0 => 'v3.17.0', + 0 => 'v3.51.0', ), ), 'nextcloud/coding-standard' => array( - 'pretty_version' => 'v1.1.1', - 'version' => '1.1.1.0', - 'reference' => '55def702fb9a37a219511e1d8c6fe8e37164c1fb', + 'pretty_version' => 'v1.2.1', + 'version' => '1.2.1.0', + 'reference' => 'cf5f18d989ec62fb4cdc7fc92a36baf34b3d829e', 'type' => 'library', 'install_path' => __DIR__ . '/../nextcloud/coding-standard', 'aliases' => array(), 'dev_requirement' => true, ), 'php-cs-fixer/shim' => array( - 'pretty_version' => 'v3.17.0', - 'version' => '3.17.0.0', - 'reference' => 'f51b4aed90565c447136f1d015798f6f7c82490f', + 'pretty_version' => 'v3.51.0', + 'version' => '3.51.0.0', + 'reference' => 'a792394f7f3934f75a4df9dca544796c6f503027', 'type' => 'application', 'install_path' => __DIR__ . '/../php-cs-fixer/shim', 'aliases' => array(), diff --git a/vendor/nextcloud/coding-standard/CHANGELOG.md b/vendor/nextcloud/coding-standard/CHANGELOG.md index 88758a3b..a71c8bc6 100644 --- a/vendor/nextcloud/coding-standard/CHANGELOG.md +++ b/vendor/nextcloud/coding-standard/CHANGELOG.md @@ -1,6 +1,33 @@ # Changelog All notable changes to this project will be documented in this file. +## 1.2.1 - 2024-02-01 +### Fix +* fix: Remove `fully_qualified_strict_types` again by @nickvergessen in https://github.com/nextcloud/coding-standard/pull/16 + +## 1.2.0 - 2024-02-01 +### Added +- `array_syntax`: Force short syntax for array +- `list_syntax`: Same for list +- ~~`fully_qualified_strict_types`: Remove namespace from classname when there is a `use` statement, and add missing backslash for global namespace~~ - Removed in 1.2.1 due to issues +- `no_leading_import_slash`: Remove leading slash from `use` statement +- `nullable_type_declaration_for_default_null_value`: Add missing `?` on type declaration for parameters defaulting to `null`. This will most likely be needed to avoid warnings in PHP 8.4. +- `yoda_style`: forbid yoda style comparision. This replaces `null === $a` by `$a === null`. + +## 1.1.1 - 2023-06-23 +### Changed +* feat: use php-cs-fixer/shim by @kesselb in https://github.com/nextcloud/coding-standard/pull/13 + +## 1.1.0 - 2023-04-13 +### Changed +* Order imports alphabetically by @come-nc in https://github.com/nextcloud/coding-standard/pull/10 +* fix(rules): Replace deprecated braces rules by @nickvergessen in https://github.com/nextcloud/coding-standard/pull/12 + +## 1.0.0 – 2021-11-10 +### Breaking change +* Update php-cs-fixer to 3.x +* See https://github.com/nextcloud/coding-standard#upgrade-from-v0x-to-v10 for instructions. + ## 0.5.0 – 2021-01-11 ### Added - New rule: short list syntax diff --git a/vendor/nextcloud/coding-standard/README.md b/vendor/nextcloud/coding-standard/README.md index 62729e3d..646b6a9f 100644 --- a/vendor/nextcloud/coding-standard/README.md +++ b/vendor/nextcloud/coding-standard/README.md @@ -46,7 +46,7 @@ For convenience you may add it to the `scripts` section of your `composer.json`: } ``` -*Note: Don't forget to exclude .php_cs.dist in your build scripts.* +*Note: Don't forget to exclude `.php-cs-fixer.dist.php` and `.php-cs-fixer.cache` in your build scripts.* ## Upgrade from v0.x to v1.0 diff --git a/vendor/nextcloud/coding-standard/src/Config.php b/vendor/nextcloud/coding-standard/src/Config.php index c6b229a0..c888eaff 100644 --- a/vendor/nextcloud/coding-standard/src/Config.php +++ b/vendor/nextcloud/coding-standard/src/Config.php @@ -18,6 +18,7 @@ public function getRules() : array { '@PSR2' => true, 'align_multiline_comment' => true, 'array_indentation' => true, + 'array_syntax' => true, 'binary_operator_spaces' => [ 'default' => 'single_space', ], @@ -35,16 +36,19 @@ public function getRules() : array { ], 'indentation_type' => true, 'line_ending' => true, + 'list_syntax' => true, 'lowercase_keywords' => true, 'method_argument_space' => [ 'on_multiline' => 'ignore', ], 'no_closing_tag' => true, + 'no_leading_import_slash' => true, 'no_spaces_after_function_name' => true, 'no_spaces_inside_parenthesis' => true, 'no_trailing_whitespace' => true, 'no_trailing_whitespace_in_comment' => true, 'no_unused_imports' => true, + 'nullable_type_declaration_for_default_null_value' => true, 'ordered_imports' => [ 'imports_order' => ['class', 'function', 'const'], 'sort_algorithm' => 'alpha' @@ -57,6 +61,7 @@ public function getRules() : array { 'visibility_required' => [ 'elements' => ['property', 'method', 'const'] ], + 'yoda_style' => ['equal' => false, 'identical' => false, 'less_and_greater' => false], ]; } } diff --git a/vendor/php-cs-fixer/shim/logo.md b/vendor/php-cs-fixer/shim/logo.md index c5f7b399..c2877f71 100644 --- a/vendor/php-cs-fixer/shim/logo.md +++ b/vendor/php-cs-fixer/shim/logo.md @@ -1,3 +1,3 @@ -The logo is © 2010-2022 Sensio Labs. +The logo is © 2010+ Sensio Labs. Original resolution can be found at https://github.com/PHP-CS-Fixer/logo . diff --git a/vendor/php-cs-fixer/shim/php-cs-fixer.phar b/vendor/php-cs-fixer/shim/php-cs-fixer.phar index 8dc906a1f81d8dc55bc1e96bd2b781e47052de6c..8182b0f73ee55402ab190b0eb651d3f740f79f61 100755 GIT binary patch delta 161423 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

`&4JA@+(A&rGa+BA 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

nDh}Q+MucYu@@e#b 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 adcR%tgR{T2=U=h<8};+%&8sM@D*HE+rX#8V diff --git a/vendor/php-cs-fixer/shim/php-cs-fixer.phar.asc b/vendor/php-cs-fixer/shim/php-cs-fixer.phar.asc index 65fbde63ae8143f6d2108cbc4b06ac9226ade0b5..aa833e9a0d91441a0e35bb372ca72ffb72ab2144 100644 GIT binary patch delta 543 zcmV+)0^t3&1hxc_B7bGyj(Y$K2@vQjFS8WskZu+`5C2|gNBjMm+2`?qUH{jV5=H5z zd;#EmZXgOXp6>N+4OZ;7fxIeKyFh!{11E0|55wd%{ksqD18-#)uM zayLaDzJu<%8?qc}OvN<@z88E8h`#H6USQ1@M#jJcZ4bUw*-~0fr+#KkBC_oG|1S=O z+o(=+_}d1#6o01pAGT3W7@1aoQ1X#}Za)pVJJ|{tjiFJ{kf3z`z)go_&TE$OO8roy zpbZmEPKA68NNXA9bprnwrxaI9VNf=~t!{Jpt2Igd&*pOD@z zY6D@~MpMTa4ih7{0^JJO*7E4$)N(qxKEzEuzB^nd(6Q}w}|>3iiLP&jLgrCU=u zBvx=e5~4}2GcTsc-Anv+gIR@?pf6&KIxjQFTE&Jmw(+j}bk76fnS*D|=0hYW6qraT zfH7@|xz|~%0m7s)km&grJu<<;opqaka&Ml!S;)d h-A0v8Y#1>c?{5q#8CyM_%mM4I=LdWRv+gJZl-KJ}5X=Ao delta 543 zcmV+)0^t3&1hxc_B7bCS$;$u=2@vQjFS8WskZz1w5B@6}o#NvAtMOc3^FE>*b&)>l(@7fCX(=mwt!(s;G9U+*x5r{aiC7y;SZ(do0*qdU72`M>=a znVX>4X}%*ROBai&c+^7!%|fvx@=?8kO}K?-j!9E%@SPNs`IR0IA2&G6&0Sj-Ip>sX zV{9Orwoua^8>ng_?>Epxi#a2!CMDY&i#c|EQXdv>&VK|42G$>Z^(8N From 6b83daf94917f75933f3d1add7022b415ca2be21 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Tue, 4 Feb 2025 15:52:27 +0100 Subject: [PATCH 11/17] chore: make index.php updater.phar MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- updater.phar | Bin 1167332 -> 1168160 bytes vendor/composer/autoload_classmap.php | 1 + vendor/composer/autoload_static.php | 1 + 3 files changed, 2 insertions(+) diff --git a/updater.phar b/updater.phar index 09762c27b0e24adb70fa0641f20ee39432e1b462..a5723c1238158c3a749e973f1e73b52a9089e856 100755 GIT binary patch delta 1391 zcma)6OKclO818J`#CGk(QPWg}w2aeGry@9O@A|PpjzS1^%Of?ta0yLkcW2{O*1Ox? zbwVXbg2J*D&-}rWYd}~Dyovx6e&%FtV}dPlm#`P zmgp`QBws||1~RE658bb$V*w$_Xz>&}F+_4wT98C7rwNk4x(pFjO;Qz-5yhOuvaDrz zfludrn!dVo8lCHf&!T}Nz@LZ(;m!pV3ZHdfu@quV>JD5w*LE1pfmpD9dm8i8kV z!!9+n(a}NObUk7iRK+Us2-e+JC1Na)%Pvz{@~VzWnUGxdd@+TXrsd%|(^~NDFii*R z9#*Uhb+P7Hm0cT6?xbC|v2Nm-naQ)~XJ)YFV0L`CRm!z|-ZGhI_AE?Xw_2e-rD`!o zbBRS`VyX@66>^z*a;t{tlkQ!1_XaX;B&OlGkt{=ZJ+|7a$L`DyKf1e3lsPi%duP_@ zo1|hJv>DAZ1)r{?Xls4CzYpWu_PfFQ_EmI)g9|Gt_{5-M**aAp)esl3Mhure7p`@` z*8|=vIu;uAv(D;^fvlq^Vc=B9QTSvPl@f#V)Ko3U-zs3&b3A8gZ)q4Orl%9^I|4g5 zxgNN-(jJDVIwS4%zgN)@9E=0k0h{Y61f`Er5B#-;24H&)bphExN5Q%hjzB5W*`9AH zcA-$fW|igO<&$yXB!ZW1Ytm*P%NW?ThZq?XC*M`l9`?ZA81ko)3oL;q72Y{i}D- zD1y1W?V-AP9W8S`zDE3imHFWQ24dhC+86>12N~KKIv9csA%-x+A%+M;l%bQMtA2kY zwp=-s;-8%*`IMZKNPRKT{nC&9!O#O^;Oaf`;uqt$KIFIV{oL{PM;!b46(?Su_!s?e B#sdHV delta 768 zcma*lUr19?90zcJbGkXFyGvVO8rQ#@r0bsDdw1_er*m2B51IPngT~z5y*C8^?tHJNzzO85~R|fXN!8M2&AVVkj@ek-#YL)KhF6bzUMrg`3KR@ zbJ3|eCr@-v49J`=t0eu1-?{$Qy<@$21O{`h#iOm6OpCQV^Uk`Pakb|B9ofnT7G7p5 z`I1Fv-V=ox+G^xv>rG?s#ig|tTx)?(`!#x@9MCu}PGsIl#EB*b1ySQgL6>D!5mZH$ z#JIwF8yvV2gN8G`pBuovgMKr(5-gvCN6+&l=QK=4dE zROS*t!3$BS@`{>nNL;{Bl{hcO14I!C(TOG}f`%^ZyhMURf*30HABQgVAA%(-k^CIG zd!WL~`)MlM0o6W3B&rbCHH8y{VnPrk!UqkaaYU39*$5g^LJkNDXJli_%;aG>=`o$B z;G-XXKBmdMaT)FahHDucK3}z$;KVI>i$AVI0sfwWLOeeO6&P+VD!>m@(1~1+!-4&7 zXTCX_hF2CmHw`ZAm<0wW(@=`N(@=#QE_#}IZzeceSO*afVZ9vg+g0RUo6&sv^y5t?qb({rw6&P#g6lD>^5Ab@2X})Y|X#q-o(iG zaLTv6QO`EA1k+FR_uzVIam3uX2yI|C--d^PO*62Lo)xG2YIqhX3zbV*sXQv5vQc)b zfO1fUl#?o=iYb>Fo@GXc7`gGZs0Jj1lUQvanL2AO+1$rom$y#_p8Zt6JYKH(j^o$L R{KIz_7cBHQMk6O8e*pB^?mYki diff --git a/vendor/composer/autoload_classmap.php b/vendor/composer/autoload_classmap.php index 3302d88e..9e980904 100644 --- a/vendor/composer/autoload_classmap.php +++ b/vendor/composer/autoload_classmap.php @@ -27,6 +27,7 @@ 'NC\\Updater\\UpdateCommand' => $baseDir . '/lib/UpdateCommand.php', 'NC\\Updater\\UpdateException' => $baseDir . '/lib/UpdateException.php', 'NC\\Updater\\Updater' => $baseDir . '/lib/Updater.php', + 'NC\\Updater\\Version' => $baseDir . '/lib/Version.php', 'Nextcloud\\CodingStandard\\Config' => $vendorDir . '/nextcloud/coding-standard/src/Config.php', 'Normalizer' => $vendorDir . '/symfony/polyfill-intl-normalizer/Resources/stubs/Normalizer.php', 'PhpToken' => $vendorDir . '/symfony/polyfill-php80/Resources/stubs/PhpToken.php', diff --git a/vendor/composer/autoload_static.php b/vendor/composer/autoload_static.php index 3e2e9de5..0a268bc1 100644 --- a/vendor/composer/autoload_static.php +++ b/vendor/composer/autoload_static.php @@ -122,6 +122,7 @@ class ComposerStaticInit936ba63ded5d1b8248cdb4d5673af0ea 'NC\\Updater\\UpdateCommand' => __DIR__ . '/../..' . '/lib/UpdateCommand.php', 'NC\\Updater\\UpdateException' => __DIR__ . '/../..' . '/lib/UpdateException.php', 'NC\\Updater\\Updater' => __DIR__ . '/../..' . '/lib/Updater.php', + 'NC\\Updater\\Version' => __DIR__ . '/../..' . '/lib/Version.php', 'Nextcloud\\CodingStandard\\Config' => __DIR__ . '/..' . '/nextcloud/coding-standard/src/Config.php', 'Normalizer' => __DIR__ . '/..' . '/symfony/polyfill-intl-normalizer/Resources/stubs/Normalizer.php', 'PhpToken' => __DIR__ . '/..' . '/symfony/polyfill-php80/Resources/stubs/PhpToken.php', From 9f0a0b719ae3b73c96c146c1d14c7d0f2d476776 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Tue, 4 Feb 2025 16:18:05 +0100 Subject: [PATCH 12/17] fix: Fix application directory listing MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- index.php | 4 ++-- lib/Updater.php | 4 ++-- updater.phar | Bin 1168160 -> 1168174 bytes 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/index.php b/index.php index 302cbd49..b68a44e7 100644 --- a/index.php +++ b/index.php @@ -277,8 +277,8 @@ private function getAppDirectories(): array { throw new \Exception('Invalid configuration in apps_paths configuration key'); } $appDir = basename($appsPath['path']); - if (strpos($appsPath['path'], $this->nextcloudDir) === 0) { - $relativePath = substr($appsPath['path'], strlen($this->nextcloudDir)); + if (strpos($appsPath['path'], $this->nextcloudDir.'/') === 0) { + $relativePath = substr($appsPath['path'], strlen($this->nextcloudDir.'/')); if ($relativePath !== 'apps') { $expected[] = $relativePath; } diff --git a/lib/Updater.php b/lib/Updater.php index 2fb49da9..3e73792f 100644 --- a/lib/Updater.php +++ b/lib/Updater.php @@ -259,8 +259,8 @@ private function getAppDirectories(): array { throw new \Exception('Invalid configuration in apps_paths configuration key'); } $appDir = basename($appsPath['path']); - if (strpos($appsPath['path'], $this->nextcloudDir) === 0) { - $relativePath = substr($appsPath['path'], strlen($this->nextcloudDir)); + if (strpos($appsPath['path'], $this->nextcloudDir.'/') === 0) { + $relativePath = substr($appsPath['path'], strlen($this->nextcloudDir.'/')); if ($relativePath !== 'apps') { $expected[] = $relativePath; } diff --git a/updater.phar b/updater.phar index a5723c1238158c3a749e973f1e73b52a9089e856..74906e86176cb46c93a3dba85789013e8680bd0e 100755 GIT binary patch delta 238 zcmZ3m%zfQ5_X+cPEDcSK4NT1w4H6R#C$2U|<-ZC-;cxa}th5!#V}Jk<9k5ufX7WWl zZvmZdh#-jm==;9DS;xLz$DR?0nShuXh*^M`6^Pk@m>q~YfS41Axqz4(hKFclz1ZW*z%>9eYL~W&&bnAZ7t#Rv=~rVs;?r0Afxc<^p1FAm#yLULfWJ zV*c$q_5v*@xD0gD6DKXR11Uz;SXa@g5n Su=(|U_S#M+pd;L!e4POB2|@e- From e23bd54c353d5cb609493257cc9373792c878d65 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Tue, 4 Feb 2025 16:26:46 +0100 Subject: [PATCH 13/17] chore: master is now 32 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- tests/features/master.feature | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/features/master.feature b/tests/features/master.feature index 4de8b06b..f1e40bd6 100644 --- a/tests/features/master.feature +++ b/tests/features/master.feature @@ -9,6 +9,6 @@ Feature: CLI updater - master base And the version number is decreased in the config.php to enforce upgrade When the CLI updater is run successfully And the output should contain "Update successful" - Then the installed version should be 31.0 + Then the installed version should be 32.0 And maintenance mode should be off And upgrade is not required From dd5f445a39455758c55f6ddd431ca02dcc591b1c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Thu, 6 Feb 2025 14:03:15 +0100 Subject: [PATCH 14/17] fix: Replace baseDir property by cleaner nextcloudDir MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- lib/Updater.php | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/lib/Updater.php b/lib/Updater.php index 3e73792f..97f9ae0a 100644 --- a/lib/Updater.php +++ b/lib/Updater.php @@ -24,7 +24,7 @@ class Updater { * @throws \Exception */ public function __construct( - private string $baseDir + string $baseDir, ) { $this->nextcloudDir = realpath(dirname($baseDir)); @@ -363,7 +363,7 @@ public function setMaintenanceMode(bool $state): void { if ($dir = getenv('NEXTCLOUD_CONFIG_DIR')) { $configFileName = rtrim($dir, '/') . '/config.php'; } else { - $configFileName = $this->baseDir . '/../config/config.php'; + $configFileName = $this->nextcloudDir . '/config/config.php'; } $this->silentLog('[info] configFileName ' . $configFileName); @@ -728,7 +728,7 @@ public function extractDownload(): void { // Ensure that the downloaded version is not lower $downloadedVersion = $this->getVersionByVersionFile(dirname($downloadedFilePath) . '/nextcloud/version.php'); - $currentVersion = $this->getVersionByVersionFile($this->baseDir . '/../version.php'); + $currentVersion = $this->getVersionByVersionFile($this->nextcloudDir . '/version.php'); if (version_compare($downloadedVersion, $currentVersion, '<')) { throw new \Exception('Downloaded version is lower than installed version'); } @@ -756,14 +756,14 @@ public function replaceEntryPoints(): void { $content = "silentLog('[info] replace ' . $file); - $parentDir = dirname($this->baseDir . '/../' . $file); + $parentDir = dirname($this->nextcloudDir . '/' . $file); if (!file_exists($parentDir)) { $r = mkdir($parentDir); if ($r !== true) { throw new \Exception('Can\'t create parent directory for entry point: ' . $file); } } - $state = file_put_contents($this->baseDir . '/../' . $file, $content); + $state = file_put_contents($this->nextcloudDir . '/' . $file, $content); if ($state === false) { throw new \Exception('Can\'t replace entry point: '.$file); } @@ -810,7 +810,7 @@ private function recursiveDelete(string $folder): void { public function deleteOldFiles(): void { $this->silentLog('[info] deleteOldFiles()'); - $shippedAppsFile = $this->baseDir . '/../core/shipped.json'; + $shippedAppsFile = $this->nextcloudDir . '/core/shipped.json'; $shippedAppsFileContent = file_get_contents($shippedAppsFile); if ($shippedAppsFileContent === false) { throw new \Exception('core/shipped.json is not available'); @@ -836,10 +836,10 @@ public function deleteOldFiles(): void { $shippedApps = array_merge($shippedApps, $newShippedApps); /** @var string $app */ foreach ($shippedApps as $app) { - $this->recursiveDelete($this->baseDir . '/../apps/' . $app); + $this->recursiveDelete($this->nextcloudDir . '/apps/' . $app); } - $configSampleFile = $this->baseDir . '/../config/config.sample.php'; + $configSampleFile = $this->nextcloudDir . '/config/config.sample.php'; if (file_exists($configSampleFile)) { $this->silentLog('[info] config sample exists'); @@ -850,7 +850,7 @@ public function deleteOldFiles(): void { } } - $themesReadme = $this->baseDir . '/../themes/README'; + $themesReadme = $this->nextcloudDir . '/themes/README'; if (file_exists($themesReadme)) { $this->silentLog('[info] themes README exists'); @@ -860,7 +860,7 @@ public function deleteOldFiles(): void { throw new \Exception('Could not delete themes README'); } } - $this->recursiveDelete($this->baseDir . '/../themes/example/'); + $this->recursiveDelete($this->nextcloudDir . '/themes/example/'); // Delete the rest $excludedElements = [ @@ -905,19 +905,19 @@ private function moveWithExclusions(string $dataLocation, array $excludedElement $fileName = explode($dataLocation, $path)[1]; if ($fileInfo->isFile()) { - if (!file_exists($this->baseDir . '/../' . dirname($fileName))) { - $state = mkdir($this->baseDir . '/../' . dirname($fileName), 0755, true); + if (!file_exists($this->nextcloudDir . '/' . dirname($fileName))) { + $state = mkdir($this->nextcloudDir . '/' . dirname($fileName), 0755, true); if ($state === false) { - throw new \Exception('Could not mkdir ' . $this->baseDir . '/../' . dirname($fileName)); + throw new \Exception('Could not mkdir ' . $this->nextcloudDir . '/' . dirname($fileName)); } } - $state = rename($path, $this->baseDir . '/../' . $fileName); + $state = rename($path, $this->nextcloudDir . '/' . $fileName); if ($state === false) { throw new \Exception( sprintf( 'Could not rename %s to %s', $path, - $this->baseDir . '/../' . $fileName + $this->nextcloudDir . '/' . $fileName ) ); } From f37bf9380d2867945389f8ca820bd2b5f03d3a18 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Thu, 6 Feb 2025 14:05:42 +0100 Subject: [PATCH 15/17] fix: Improve variable names MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- lib/Updater.php | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/lib/Updater.php b/lib/Updater.php index 97f9ae0a..49146162 100644 --- a/lib/Updater.php +++ b/lib/Updater.php @@ -303,7 +303,6 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa yield $path => new \SplFileInfo($path); } - closedir($handle); } @@ -408,25 +407,26 @@ public function createBackup(): void { throw new \Exception('Could not create backup folder location'); } - foreach ($this->getRecursiveDirectoryIterator($this->nextcloudDir, $excludedElements) as $path => $fileInfo) { - $fileName = explode($this->nextcloudDir, $path)[1]; + foreach ($this->getRecursiveDirectoryIterator($this->nextcloudDir, $excludedElements) as $absolutePath => $fileInfo) { + $relativePath = explode($this->nextcloudDir, $absolutePath)[1]; + $relativeDirectory = dirname($relativePath); // Create folder if it doesn't exist - if (!file_exists($backupFolderLocation . '/' . dirname($fileName))) { - $state = mkdir($backupFolderLocation . '/' . dirname($fileName), 0750, true); + if (!file_exists($backupFolderLocation . '/' . $relativeDirectory)) { + $state = mkdir($backupFolderLocation . '/' . $relativeDirectory, 0750, true); if ($state === false) { - throw new \Exception('Could not create folder: '.$backupFolderLocation.'/'.dirname($fileName)); + throw new \Exception('Could not create folder: '.$backupFolderLocation.'/'.$relativeDirectory); } } // If it is a file copy it if ($fileInfo->isFile()) { - $state = copy($fileInfo->getRealPath(), $backupFolderLocation . $fileName); + $state = copy($fileInfo->getRealPath(), $backupFolderLocation . $relativePath); if ($state === false) { $message = sprintf( 'Could not copy "%s" to "%s"', $fileInfo->getRealPath(), - $backupFolderLocation . $fileName + $backupFolderLocation . $relativePath ); if (is_readable($fileInfo->getRealPath()) === false) { @@ -437,11 +437,11 @@ public function createBackup(): void { ); } - if (is_writable($backupFolderLocation . $fileName) === false) { + if (is_writable($backupFolderLocation . $relativePath) === false) { $message = sprintf( '%s. Destination %s is not writable', $message, - $backupFolderLocation . $fileName + $backupFolderLocation . $relativePath ); } From 1d900495021601564545ee0007508a4abe0a668b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Thu, 6 Feb 2025 14:09:09 +0100 Subject: [PATCH 16/17] fix: Store first level children in an array to avoid problems MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- lib/Updater.php | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/lib/Updater.php b/lib/Updater.php index 49146162..5fb21b89 100644 --- a/lib/Updater.php +++ b/lib/Updater.php @@ -289,6 +289,9 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa if ($handle === false) { throw new \Exception('Could not open '.$folder); } + + /* Store first level children in an array to avoid trouble if changes happen while iterating */ + $children = []; while ($name = readdir($handle)) { if (in_array($name, ['.', '..'])) { continue; @@ -296,14 +299,18 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa if (isset($exclusions[$name])) { continue; } + $children[] = $name; + } + + closedir($handle); + + foreach ($children as $name) { $path = $folder.'/'.$name; if (is_dir($path)) { yield from $this->getRecursiveDirectoryIterator($path, []); } yield $path => new \SplFileInfo($path); } - - closedir($handle); } /** From 0c05ada12bef48aa0f59fc2153f3b69100448e64 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B4me=20Chilliet?= Date: Thu, 6 Feb 2025 14:12:18 +0100 Subject: [PATCH 17/17] chore: make updater.phar index.php MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Côme Chilliet --- index.php | 61 ++++++++++++++++++++++++++++----------------------- updater.phar | Bin 1168174 -> 1168454 bytes 2 files changed, 34 insertions(+), 27 deletions(-) diff --git a/index.php b/index.php index b68a44e7..ada1679c 100644 --- a/index.php +++ b/index.php @@ -42,7 +42,7 @@ class Updater { * @throws \Exception */ public function __construct( - private string $baseDir + string $baseDir, ) { $this->nextcloudDir = realpath(dirname($baseDir)); @@ -307,6 +307,9 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa if ($handle === false) { throw new \Exception('Could not open '.$folder); } + + /* Store first level children in an array to avoid trouble if changes happen while iterating */ + $children = []; while ($name = readdir($handle)) { if (in_array($name, ['.', '..'])) { continue; @@ -314,15 +317,18 @@ private function getRecursiveDirectoryIterator(string $folder, array $excludedPa if (isset($exclusions[$name])) { continue; } + $children[] = $name; + } + + closedir($handle); + + foreach ($children as $name) { $path = $folder.'/'.$name; if (is_dir($path)) { yield from $this->getRecursiveDirectoryIterator($path, []); } yield $path => new \SplFileInfo($path); } - - - closedir($handle); } /** @@ -381,7 +387,7 @@ public function setMaintenanceMode(bool $state): void { if ($dir = getenv('NEXTCLOUD_CONFIG_DIR')) { $configFileName = rtrim($dir, '/') . '/config.php'; } else { - $configFileName = $this->baseDir . '/../config/config.php'; + $configFileName = $this->nextcloudDir . '/config/config.php'; } $this->silentLog('[info] configFileName ' . $configFileName); @@ -426,25 +432,26 @@ public function createBackup(): void { throw new \Exception('Could not create backup folder location'); } - foreach ($this->getRecursiveDirectoryIterator($this->nextcloudDir, $excludedElements) as $path => $fileInfo) { - $fileName = explode($this->nextcloudDir, $path)[1]; + foreach ($this->getRecursiveDirectoryIterator($this->nextcloudDir, $excludedElements) as $absolutePath => $fileInfo) { + $relativePath = explode($this->nextcloudDir, $absolutePath)[1]; + $relativeDirectory = dirname($relativePath); // Create folder if it doesn't exist - if (!file_exists($backupFolderLocation . '/' . dirname($fileName))) { - $state = mkdir($backupFolderLocation . '/' . dirname($fileName), 0750, true); + if (!file_exists($backupFolderLocation . '/' . $relativeDirectory)) { + $state = mkdir($backupFolderLocation . '/' . $relativeDirectory, 0750, true); if ($state === false) { - throw new \Exception('Could not create folder: '.$backupFolderLocation.'/'.dirname($fileName)); + throw new \Exception('Could not create folder: '.$backupFolderLocation.'/'.$relativeDirectory); } } // If it is a file copy it if ($fileInfo->isFile()) { - $state = copy($fileInfo->getRealPath(), $backupFolderLocation . $fileName); + $state = copy($fileInfo->getRealPath(), $backupFolderLocation . $relativePath); if ($state === false) { $message = sprintf( 'Could not copy "%s" to "%s"', $fileInfo->getRealPath(), - $backupFolderLocation . $fileName + $backupFolderLocation . $relativePath ); if (is_readable($fileInfo->getRealPath()) === false) { @@ -455,11 +462,11 @@ public function createBackup(): void { ); } - if (is_writable($backupFolderLocation . $fileName) === false) { + if (is_writable($backupFolderLocation . $relativePath) === false) { $message = sprintf( '%s. Destination %s is not writable', $message, - $backupFolderLocation . $fileName + $backupFolderLocation . $relativePath ); } @@ -746,7 +753,7 @@ public function extractDownload(): void { // Ensure that the downloaded version is not lower $downloadedVersion = $this->getVersionByVersionFile(dirname($downloadedFilePath) . '/nextcloud/version.php'); - $currentVersion = $this->getVersionByVersionFile($this->baseDir . '/../version.php'); + $currentVersion = $this->getVersionByVersionFile($this->nextcloudDir . '/version.php'); if (version_compare($downloadedVersion, $currentVersion, '<')) { throw new \Exception('Downloaded version is lower than installed version'); } @@ -774,14 +781,14 @@ public function replaceEntryPoints(): void { $content = "silentLog('[info] replace ' . $file); - $parentDir = dirname($this->baseDir . '/../' . $file); + $parentDir = dirname($this->nextcloudDir . '/' . $file); if (!file_exists($parentDir)) { $r = mkdir($parentDir); if ($r !== true) { throw new \Exception('Can\'t create parent directory for entry point: ' . $file); } } - $state = file_put_contents($this->baseDir . '/../' . $file, $content); + $state = file_put_contents($this->nextcloudDir . '/' . $file, $content); if ($state === false) { throw new \Exception('Can\'t replace entry point: '.$file); } @@ -828,7 +835,7 @@ private function recursiveDelete(string $folder): void { public function deleteOldFiles(): void { $this->silentLog('[info] deleteOldFiles()'); - $shippedAppsFile = $this->baseDir . '/../core/shipped.json'; + $shippedAppsFile = $this->nextcloudDir . '/core/shipped.json'; $shippedAppsFileContent = file_get_contents($shippedAppsFile); if ($shippedAppsFileContent === false) { throw new \Exception('core/shipped.json is not available'); @@ -854,10 +861,10 @@ public function deleteOldFiles(): void { $shippedApps = array_merge($shippedApps, $newShippedApps); /** @var string $app */ foreach ($shippedApps as $app) { - $this->recursiveDelete($this->baseDir . '/../apps/' . $app); + $this->recursiveDelete($this->nextcloudDir . '/apps/' . $app); } - $configSampleFile = $this->baseDir . '/../config/config.sample.php'; + $configSampleFile = $this->nextcloudDir . '/config/config.sample.php'; if (file_exists($configSampleFile)) { $this->silentLog('[info] config sample exists'); @@ -868,7 +875,7 @@ public function deleteOldFiles(): void { } } - $themesReadme = $this->baseDir . '/../themes/README'; + $themesReadme = $this->nextcloudDir . '/themes/README'; if (file_exists($themesReadme)) { $this->silentLog('[info] themes README exists'); @@ -878,7 +885,7 @@ public function deleteOldFiles(): void { throw new \Exception('Could not delete themes README'); } } - $this->recursiveDelete($this->baseDir . '/../themes/example/'); + $this->recursiveDelete($this->nextcloudDir . '/themes/example/'); // Delete the rest $excludedElements = [ @@ -923,19 +930,19 @@ private function moveWithExclusions(string $dataLocation, array $excludedElement $fileName = explode($dataLocation, $path)[1]; if ($fileInfo->isFile()) { - if (!file_exists($this->baseDir . '/../' . dirname($fileName))) { - $state = mkdir($this->baseDir . '/../' . dirname($fileName), 0755, true); + if (!file_exists($this->nextcloudDir . '/' . dirname($fileName))) { + $state = mkdir($this->nextcloudDir . '/' . dirname($fileName), 0755, true); if ($state === false) { - throw new \Exception('Could not mkdir ' . $this->baseDir . '/../' . dirname($fileName)); + throw new \Exception('Could not mkdir ' . $this->nextcloudDir . '/' . dirname($fileName)); } } - $state = rename($path, $this->baseDir . '/../' . $fileName); + $state = rename($path, $this->nextcloudDir . '/' . $fileName); if ($state === false) { throw new \Exception( sprintf( 'Could not rename %s to %s', $path, - $this->baseDir . '/../' . $fileName + $this->nextcloudDir . '/' . $fileName ) ); } diff --git a/updater.phar b/updater.phar index 74906e86176cb46c93a3dba85789013e8680bd0e..3c086b874900f056cd67a37ee2b1a8663c6a43ac 100755 GIT binary patch delta 924 zcmZuwOKTHR6t-#8G_N+ts>Mg`Eetj(sZCn*GA1o0SRaU@xRB7rB)Ms(jx%9q@}ia& zR76lr5xhbd?nEevwa9=!K)Mh_TpvZ-+97)^UgXF{c4N9ey;6ativ9yet7aJe$kb9xUccl|6d;DR_=Hw?t3TN z5GF)Bq61+@bRsN>E`$|fL)Z}xgcH$?=+V6suDcty;K-~$6Y=>@Mf7(Tm}_^bnj%QE zgiG-%O$drtkJ>@%U$j}Rqr>EyCM%R=1x3|}NQ+b?>6{>D6epGi8AImg*t#34m;W9o zXGn~25`T-Ts(xjf18?(95c)L2Xg$ z_9$$fs4uTy?@7Told(q=g{_9A|E6%T!!QTt;H=p=*JKzo$hR^C+6;3$4`j!5D?oOn z*F!MCiY4eXBGEm>-jpESbohumV4C99#VQEb(YwKU!NE VTl?|&!1iivW7CAUX?p6?)E_v~EkytT delta 741 zcmX@M!hPK`_X+cPEDcSK4NT1w4H6R#C$2U|<-ZC-;cxa}Y_(+xSgckv`J$b-fKE39 z7=Y-HzVGXsb?n=9>=}WW35c12m<5PgftU@5*@2h?h&h3n3y8UamKHGp_*&D zLY1J{_5g0dAld2Snu4>YvuX)06XD|Gol9pf^ z8#~m9={+k1m8Wyq3rb8^C=_Jd-ef3vmvwrt9+3aOTu^lS40AzIj)KIJ49#f6*y(T0 z1!JdgsSp&JUSA=|IX%@vP#44%pT5#Uuxz?rrJ&?=3roRH_O#5LRKLXB>FX^7Ri}Tn z6s+KYilk02wG#Zn3FB!_KWHH+JpF)`pyKp()`CF@WxCctQ=gXtT@ddl$h+OuMsR}~ zAJokXdJ5|LdV1SglLbFAp$SfBOA~y>4^s$Lxh-8#j0H{McC~ClcUCmP>9qxd#%N;O z4-^QRF`^5y6$vV02$~lQDq