aboutsummaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
Diffstat (limited to 'lib')
-rw-r--r--lib/autoloader.php12
-rw-r--r--lib/base.php22
-rw-r--r--lib/composer/composer/autoload_classmap.php2
-rw-r--r--lib/composer/composer/autoload_static.php2
-rw-r--r--lib/l10n/cs.js2
-rw-r--r--lib/l10n/cs.json2
-rw-r--r--lib/l10n/de.js4
-rw-r--r--lib/l10n/de.json4
-rw-r--r--lib/l10n/de_DE.js2
-rw-r--r--lib/l10n/de_DE.json2
-rw-r--r--lib/l10n/en_GB.js2
-rw-r--r--lib/l10n/en_GB.json2
-rw-r--r--lib/l10n/es.js2
-rw-r--r--lib/l10n/es.json2
-rw-r--r--lib/l10n/et_EE.js2
-rw-r--r--lib/l10n/et_EE.json2
-rw-r--r--lib/l10n/ga.js2
-rw-r--r--lib/l10n/ga.json2
-rw-r--r--lib/l10n/it.js2
-rw-r--r--lib/l10n/it.json2
-rw-r--r--lib/l10n/pl.js2
-rw-r--r--lib/l10n/pl.json2
-rw-r--r--lib/l10n/pt_BR.js6
-rw-r--r--lib/l10n/pt_BR.json6
-rw-r--r--lib/l10n/sr.js2
-rw-r--r--lib/l10n/sr.json2
-rw-r--r--lib/l10n/sv.js2
-rw-r--r--lib/l10n/sv.json2
-rw-r--r--lib/l10n/zh_CN.js2
-rw-r--r--lib/l10n/zh_CN.json2
-rw-r--r--lib/l10n/zh_HK.js2
-rw-r--r--lib/l10n/zh_HK.json2
-rw-r--r--lib/l10n/zh_TW.js2
-rw-r--r--lib/l10n/zh_TW.json2
-rw-r--r--lib/private/Accounts/AccountManager.php4
-rw-r--r--lib/private/Accounts/AccountProperty.php24
-rw-r--r--lib/private/AppFramework/Bootstrap/Coordinator.php7
-rw-r--r--lib/private/AppFramework/Utility/SimpleContainer.php8
-rw-r--r--lib/private/Calendar/Manager.php137
-rw-r--r--lib/private/DB/Adapter.php20
-rw-r--r--lib/private/DB/AdapterOCI8.php2
-rw-r--r--lib/private/DB/AdapterPgSql.php2
-rw-r--r--lib/private/DB/Connection.php29
-rw-r--r--lib/private/Encryption/EncryptionEventListener.php93
-rw-r--r--lib/private/Encryption/EncryptionWrapper.php10
-rw-r--r--lib/private/Encryption/HookManager.php75
-rw-r--r--lib/private/Encryption/Update.php130
-rw-r--r--lib/private/Encryption/Util.php2
-rw-r--r--lib/private/Files/Cache/Wrapper/CacheJail.php13
-rw-r--r--lib/private/Files/SimpleFS/SimpleFile.php10
-rw-r--r--lib/private/Files/Storage/Temporary.php8
-rw-r--r--lib/private/Files/Storage/Wrapper/Encryption.php29
-rw-r--r--lib/private/Files/Type/Detection.php7
-rw-r--r--lib/private/Installer.php7
-rw-r--r--lib/private/Log/LogDetails.php4
-rw-r--r--lib/private/Repair/MoveUpdaterStepFile.php3
-rw-r--r--lib/private/Route/Router.php10
-rw-r--r--lib/private/Security/RateLimiting/Limiter.php7
-rw-r--r--lib/private/ServerContainer.php23
-rw-r--r--lib/private/TempManager.php3
-rw-r--r--lib/private/User/User.php5
-rw-r--r--lib/private/legacy/OC_Helper.php89
-rw-r--r--lib/private/legacy/OC_Util.php2
-rw-r--r--lib/public/Accounts/IAccountManager.php28
-rw-r--r--lib/public/Files.php36
-rw-r--r--lib/public/Files/SimpleFS/ISimpleFile.php10
-rw-r--r--lib/public/Template.php2
-rw-r--r--lib/public/Util.php59
68 files changed, 558 insertions, 450 deletions
diff --git a/lib/autoloader.php b/lib/autoloader.php
index 41b272a457c..7084eb93c89 100644
--- a/lib/autoloader.php
+++ b/lib/autoloader.php
@@ -22,10 +22,8 @@ class Autoloader {
/**
* Optional low-latency memory cache for class to path mapping.
- *
- * @var \OC\Memcache\Cache
*/
- protected $memoryCache;
+ protected ?ICache $memoryCache = null;
/**
* Autoloader constructor.
@@ -127,15 +125,15 @@ class Autoloader {
* @throws AutoloadNotAllowedException
*/
public function load(string $class): bool {
+ if (class_exists($class, false)) {
+ return false;
+ }
+
$pathsToRequire = null;
if ($this->memoryCache) {
$pathsToRequire = $this->memoryCache->get($class);
}
- if (class_exists($class, false)) {
- return false;
- }
-
if (!is_array($pathsToRequire)) {
// No cache or cache miss
$pathsToRequire = [];
diff --git a/lib/base.php b/lib/base.php
index aa463e206a3..45058db1600 100644
--- a/lib/base.php
+++ b/lib/base.php
@@ -6,13 +6,14 @@ declare(strict_types=1);
* SPDX-FileCopyrightText: 2013-2016 ownCloud, Inc.
* SPDX-License-Identifier: AGPL-3.0-only
*/
-use OC\Encryption\HookManager;
+
use OC\Profiler\BuiltInProfiler;
use OC\Share20\GroupDeletedListener;
use OC\Share20\Hooks;
use OC\Share20\UserDeletedListener;
use OC\Share20\UserRemovedListener;
use OCP\EventDispatcher\IEventDispatcher;
+use OCP\Files\Events\BeforeFileSystemSetupEvent;
use OCP\Group\Events\GroupDeletedEvent;
use OCP\Group\Events\UserRemovedEvent;
use OCP\IConfig;
@@ -22,7 +23,6 @@ use OCP\IURLGenerator;
use OCP\IUserSession;
use OCP\Security\Bruteforce\IThrottler;
use OCP\Server;
-use OCP\Share;
use OCP\Template\ITemplateManager;
use OCP\User\Events\UserChangedEvent;
use OCP\User\Events\UserDeletedEvent;
@@ -188,8 +188,6 @@ class OC {
}
public static function checkConfig(): void {
- $l = Server::get(\OCP\L10N\IFactory::class)->get('lib');
-
// Create config if it does not already exist
$configFilePath = self::$configDir . '/config.php';
if (!file_exists($configFilePath)) {
@@ -201,6 +199,7 @@ class OC {
if (!$configFileWritable && !OC_Helper::isReadOnlyConfigEnabled()
|| !$configFileWritable && \OCP\Util::needUpgrade()) {
$urlGenerator = Server::get(IURLGenerator::class);
+ $l = Server::get(\OCP\L10N\IFactory::class)->get('lib');
if (self::$CLI) {
echo $l->t('Cannot write into "config" directory!') . "\n";
@@ -711,6 +710,7 @@ class OC {
self::performSameSiteCookieProtection($config);
if (!defined('OC_CONSOLE')) {
+ $eventLogger->start('check_server', 'Run a few configuration checks');
$errors = OC_Util::checkServer($systemConfig);
if (count($errors) > 0) {
if (!self::$CLI) {
@@ -745,6 +745,7 @@ class OC {
} elseif (self::$CLI && $config->getSystemValueBool('installed', false)) {
$config->deleteAppValue('core', 'cronErrors');
}
+ $eventLogger->end('check_server');
}
// User and Groups
@@ -752,6 +753,7 @@ class OC {
self::$server->getSession()->set('user_id', '');
}
+ $eventLogger->start('setup_backends', 'Setup group and user backends');
Server::get(\OCP\IUserManager::class)->registerBackend(new \OC\User\Database());
Server::get(\OCP\IGroupManager::class)->addBackend(new \OC\Group\Database());
@@ -770,6 +772,7 @@ class OC {
// Run upgrades in incognito mode
OC_User::setIncognitoMode(true);
}
+ $eventLogger->end('setup_backends');
self::registerCleanupHooks($systemConfig);
self::registerShareHooks($systemConfig);
@@ -907,15 +910,16 @@ class OC {
}
private static function registerEncryptionWrapperAndHooks(): void {
+ /** @var \OC\Encryption\Manager */
$manager = Server::get(\OCP\Encryption\IManager::class);
- \OCP\Util::connectHook('OC_Filesystem', 'preSetup', $manager, 'setupStorage');
+ Server::get(IEventDispatcher::class)->addListener(
+ BeforeFileSystemSetupEvent::class,
+ $manager->setupStorage(...),
+ );
$enabled = $manager->isEnabled();
if ($enabled) {
- \OCP\Util::connectHook(Share::class, 'post_shared', HookManager::class, 'postShared');
- \OCP\Util::connectHook(Share::class, 'post_unshare', HookManager::class, 'postUnshared');
- \OCP\Util::connectHook('OC_Filesystem', 'post_rename', HookManager::class, 'postRename');
- \OCP\Util::connectHook('\OCA\Files_Trashbin\Trashbin', 'post_restore', HookManager::class, 'postRestore');
+ \OC\Encryption\EncryptionEventListener::register(Server::get(IEventDispatcher::class));
}
}
diff --git a/lib/composer/composer/autoload_classmap.php b/lib/composer/composer/autoload_classmap.php
index f15d4e2d55f..856afbe5677 100644
--- a/lib/composer/composer/autoload_classmap.php
+++ b/lib/composer/composer/autoload_classmap.php
@@ -1539,6 +1539,7 @@ return array(
'OC\\DirectEditing\\Token' => $baseDir . '/lib/private/DirectEditing/Token.php',
'OC\\EmojiHelper' => $baseDir . '/lib/private/EmojiHelper.php',
'OC\\Encryption\\DecryptAll' => $baseDir . '/lib/private/Encryption/DecryptAll.php',
+ 'OC\\Encryption\\EncryptionEventListener' => $baseDir . '/lib/private/Encryption/EncryptionEventListener.php',
'OC\\Encryption\\EncryptionWrapper' => $baseDir . '/lib/private/Encryption/EncryptionWrapper.php',
'OC\\Encryption\\Exceptions\\DecryptionFailedException' => $baseDir . '/lib/private/Encryption/Exceptions/DecryptionFailedException.php',
'OC\\Encryption\\Exceptions\\EmptyEncryptionDataException' => $baseDir . '/lib/private/Encryption/Exceptions/EmptyEncryptionDataException.php',
@@ -1549,7 +1550,6 @@ return array(
'OC\\Encryption\\Exceptions\\ModuleDoesNotExistsException' => $baseDir . '/lib/private/Encryption/Exceptions/ModuleDoesNotExistsException.php',
'OC\\Encryption\\Exceptions\\UnknownCipherException' => $baseDir . '/lib/private/Encryption/Exceptions/UnknownCipherException.php',
'OC\\Encryption\\File' => $baseDir . '/lib/private/Encryption/File.php',
- 'OC\\Encryption\\HookManager' => $baseDir . '/lib/private/Encryption/HookManager.php',
'OC\\Encryption\\Keys\\Storage' => $baseDir . '/lib/private/Encryption/Keys/Storage.php',
'OC\\Encryption\\Manager' => $baseDir . '/lib/private/Encryption/Manager.php',
'OC\\Encryption\\Update' => $baseDir . '/lib/private/Encryption/Update.php',
diff --git a/lib/composer/composer/autoload_static.php b/lib/composer/composer/autoload_static.php
index dfb238acbf3..fed9723421e 100644
--- a/lib/composer/composer/autoload_static.php
+++ b/lib/composer/composer/autoload_static.php
@@ -1580,6 +1580,7 @@ class ComposerStaticInit749170dad3f5e7f9ca158f5a9f04f6a2
'OC\\DirectEditing\\Token' => __DIR__ . '/../../..' . '/lib/private/DirectEditing/Token.php',
'OC\\EmojiHelper' => __DIR__ . '/../../..' . '/lib/private/EmojiHelper.php',
'OC\\Encryption\\DecryptAll' => __DIR__ . '/../../..' . '/lib/private/Encryption/DecryptAll.php',
+ 'OC\\Encryption\\EncryptionEventListener' => __DIR__ . '/../../..' . '/lib/private/Encryption/EncryptionEventListener.php',
'OC\\Encryption\\EncryptionWrapper' => __DIR__ . '/../../..' . '/lib/private/Encryption/EncryptionWrapper.php',
'OC\\Encryption\\Exceptions\\DecryptionFailedException' => __DIR__ . '/../../..' . '/lib/private/Encryption/Exceptions/DecryptionFailedException.php',
'OC\\Encryption\\Exceptions\\EmptyEncryptionDataException' => __DIR__ . '/../../..' . '/lib/private/Encryption/Exceptions/EmptyEncryptionDataException.php',
@@ -1590,7 +1591,6 @@ class ComposerStaticInit749170dad3f5e7f9ca158f5a9f04f6a2
'OC\\Encryption\\Exceptions\\ModuleDoesNotExistsException' => __DIR__ . '/../../..' . '/lib/private/Encryption/Exceptions/ModuleDoesNotExistsException.php',
'OC\\Encryption\\Exceptions\\UnknownCipherException' => __DIR__ . '/../../..' . '/lib/private/Encryption/Exceptions/UnknownCipherException.php',
'OC\\Encryption\\File' => __DIR__ . '/../../..' . '/lib/private/Encryption/File.php',
- 'OC\\Encryption\\HookManager' => __DIR__ . '/../../..' . '/lib/private/Encryption/HookManager.php',
'OC\\Encryption\\Keys\\Storage' => __DIR__ . '/../../..' . '/lib/private/Encryption/Keys/Storage.php',
'OC\\Encryption\\Manager' => __DIR__ . '/../../..' . '/lib/private/Encryption/Manager.php',
'OC\\Encryption\\Update' => __DIR__ . '/../../..' . '/lib/private/Encryption/Update.php',
diff --git a/lib/l10n/cs.js b/lib/l10n/cs.js
index 2233f31f686..b4304fb14ab 100644
--- a/lib/l10n/cs.js
+++ b/lib/l10n/cs.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "Cíl neexistuje",
"Destination is not creatable" : "Cíl není možné vytvořit",
"Dot files are not allowed" : "Názvy souborů, začínající na tečku nejsou dovolené",
+ "%1$s (renamed)" : "%1$s (přejmenované)",
+ "renamed file" : "přejmenovaný soubor",
"\"%1$s\" is a forbidden file or folder name." : "„%1$s“ je zakázáno v názvu souboru nebo složky.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "„%1$s“ je zakázaná předpona pro názvy souborů či složek.",
"\"%1$s\" is not allowed inside a file or folder name." : "„%1$s“ není povoleno v rámci názvu souboru či složky.",
diff --git a/lib/l10n/cs.json b/lib/l10n/cs.json
index 087e2244eeb..f6cb00467cb 100644
--- a/lib/l10n/cs.json
+++ b/lib/l10n/cs.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "Cíl neexistuje",
"Destination is not creatable" : "Cíl není možné vytvořit",
"Dot files are not allowed" : "Názvy souborů, začínající na tečku nejsou dovolené",
+ "%1$s (renamed)" : "%1$s (přejmenované)",
+ "renamed file" : "přejmenovaný soubor",
"\"%1$s\" is a forbidden file or folder name." : "„%1$s“ je zakázáno v názvu souboru nebo složky.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "„%1$s“ je zakázaná předpona pro názvy souborů či složek.",
"\"%1$s\" is not allowed inside a file or folder name." : "„%1$s“ není povoleno v rámci názvu souboru či složky.",
diff --git a/lib/l10n/de.js b/lib/l10n/de.js
index 672c6ca4f25..e44f2b89e2b 100644
--- a/lib/l10n/de.js
+++ b/lib/l10n/de.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "Ziel existiert nicht",
"Destination is not creatable" : "Ziel kann nicht erstellt werden",
"Dot files are not allowed" : "Dateinamen mit einem Punkt am Anfang sind nicht erlaubt",
+ "%1$s (renamed)" : "%1$s (umbenannt)",
+ "renamed file" : "Umbenannte Datei",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" ist ein unzulässiger Datei- oder Ordnername.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" ist ein unzulässiges Präfix für Datei- oder Ordnernamen.",
"\"%1$s\" is not allowed inside a file or folder name." : "\"%1$s\" ist in einem Datei- oder Ordnernamen unzulässig.",
@@ -120,7 +122,7 @@ OC.L10N.register(
"__language_name__" : "Deutsch (Persönlich: Du)",
"This is an automatically sent email, please do not reply." : "Dies ist eine automatisch gesendete E-Mail. Bitte antworte nicht auf diese E-Mail.",
"Help & privacy" : "Hilfe & Datenschutz",
- "Appearance and accessibility" : "Erscheinungsbild und Barrierefreiheit",
+ "Appearance and accessibility" : "Aussehen und Barrierefreiheit",
"Apps" : "Apps",
"Personal settings" : "Persönliche Einstellungen",
"Administration settings" : "Verwaltungseinstellungen",
diff --git a/lib/l10n/de.json b/lib/l10n/de.json
index 17ce3b96f49..7a05dfc101f 100644
--- a/lib/l10n/de.json
+++ b/lib/l10n/de.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "Ziel existiert nicht",
"Destination is not creatable" : "Ziel kann nicht erstellt werden",
"Dot files are not allowed" : "Dateinamen mit einem Punkt am Anfang sind nicht erlaubt",
+ "%1$s (renamed)" : "%1$s (umbenannt)",
+ "renamed file" : "Umbenannte Datei",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" ist ein unzulässiger Datei- oder Ordnername.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" ist ein unzulässiges Präfix für Datei- oder Ordnernamen.",
"\"%1$s\" is not allowed inside a file or folder name." : "\"%1$s\" ist in einem Datei- oder Ordnernamen unzulässig.",
@@ -118,7 +120,7 @@
"__language_name__" : "Deutsch (Persönlich: Du)",
"This is an automatically sent email, please do not reply." : "Dies ist eine automatisch gesendete E-Mail. Bitte antworte nicht auf diese E-Mail.",
"Help & privacy" : "Hilfe & Datenschutz",
- "Appearance and accessibility" : "Erscheinungsbild und Barrierefreiheit",
+ "Appearance and accessibility" : "Aussehen und Barrierefreiheit",
"Apps" : "Apps",
"Personal settings" : "Persönliche Einstellungen",
"Administration settings" : "Verwaltungseinstellungen",
diff --git a/lib/l10n/de_DE.js b/lib/l10n/de_DE.js
index aa926c96d4f..4bfd5faa7f2 100644
--- a/lib/l10n/de_DE.js
+++ b/lib/l10n/de_DE.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "Ziel existiert nicht",
"Destination is not creatable" : "Ziel kann nicht erstellt werden",
"Dot files are not allowed" : "Dateinamen mit einem Punkt am Anfang sind nicht erlaubt",
+ "%1$s (renamed)" : "%1$s (umbenannt)",
+ "renamed file" : "Umbenannte Datei",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" ist ein verbotener Datei- oder Ordnername.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" ist ein verbotenes Präfix für Datei- oder Ordnernamen.",
"\"%1$s\" is not allowed inside a file or folder name." : "\"%1$s\" ist in einem Datei- oder Ordnernamen unzulässig.",
diff --git a/lib/l10n/de_DE.json b/lib/l10n/de_DE.json
index f23493df570..6faebb2c6c0 100644
--- a/lib/l10n/de_DE.json
+++ b/lib/l10n/de_DE.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "Ziel existiert nicht",
"Destination is not creatable" : "Ziel kann nicht erstellt werden",
"Dot files are not allowed" : "Dateinamen mit einem Punkt am Anfang sind nicht erlaubt",
+ "%1$s (renamed)" : "%1$s (umbenannt)",
+ "renamed file" : "Umbenannte Datei",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" ist ein verbotener Datei- oder Ordnername.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" ist ein verbotenes Präfix für Datei- oder Ordnernamen.",
"\"%1$s\" is not allowed inside a file or folder name." : "\"%1$s\" ist in einem Datei- oder Ordnernamen unzulässig.",
diff --git a/lib/l10n/en_GB.js b/lib/l10n/en_GB.js
index 2494ab4aca4..d6a8da225ba 100644
--- a/lib/l10n/en_GB.js
+++ b/lib/l10n/en_GB.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "Destination does not exist",
"Destination is not creatable" : "Destination is not creatable",
"Dot files are not allowed" : "Dot files are not allowed",
+ "%1$s (renamed)" : "%1$s (renamed)",
+ "renamed file" : "renamed file",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" is a forbidden file or folder name.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" is a forbidden prefix for file or folder names.",
"\"%1$s\" is not allowed inside a file or folder name." : "\"%1$s\" is not allowed inside a file or folder name.",
diff --git a/lib/l10n/en_GB.json b/lib/l10n/en_GB.json
index 08e84f39af1..e1bd150aca6 100644
--- a/lib/l10n/en_GB.json
+++ b/lib/l10n/en_GB.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "Destination does not exist",
"Destination is not creatable" : "Destination is not creatable",
"Dot files are not allowed" : "Dot files are not allowed",
+ "%1$s (renamed)" : "%1$s (renamed)",
+ "renamed file" : "renamed file",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" is a forbidden file or folder name.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" is a forbidden prefix for file or folder names.",
"\"%1$s\" is not allowed inside a file or folder name." : "\"%1$s\" is not allowed inside a file or folder name.",
diff --git a/lib/l10n/es.js b/lib/l10n/es.js
index a3cf61509ec..e4076a5cc2c 100644
--- a/lib/l10n/es.js
+++ b/lib/l10n/es.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "El destino no existe",
"Destination is not creatable" : "El destino no se puede crear",
"Dot files are not allowed" : "Los archivos Dot no están permitidos",
+ "%1$s (renamed)" : "%1$s (renombrado)",
+ "renamed file" : "archivo renombrado",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" Es un nombre de archivo o carpeta no permitido.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "%1$s es un prefijo prohibido para nombres de archivo o carpeta.",
"\"%1$s\" is not allowed inside a file or folder name." : "«%1$s» no se permite en el nombre de un archivo o carpeta.",
diff --git a/lib/l10n/es.json b/lib/l10n/es.json
index 34d4db2eec4..ba3043cee36 100644
--- a/lib/l10n/es.json
+++ b/lib/l10n/es.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "El destino no existe",
"Destination is not creatable" : "El destino no se puede crear",
"Dot files are not allowed" : "Los archivos Dot no están permitidos",
+ "%1$s (renamed)" : "%1$s (renombrado)",
+ "renamed file" : "archivo renombrado",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" Es un nombre de archivo o carpeta no permitido.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "%1$s es un prefijo prohibido para nombres de archivo o carpeta.",
"\"%1$s\" is not allowed inside a file or folder name." : "«%1$s» no se permite en el nombre de un archivo o carpeta.",
diff --git a/lib/l10n/et_EE.js b/lib/l10n/et_EE.js
index 7932c79256b..ae5999fc496 100644
--- a/lib/l10n/et_EE.js
+++ b/lib/l10n/et_EE.js
@@ -84,6 +84,8 @@ OC.L10N.register(
"Destination does not exist" : "Sihtmeediat pole olemas",
"Destination is not creatable" : "Sihtmeedia pole loodav",
"Dot files are not allowed" : "Punktiga failid pole lubatud",
+ "%1$s (renamed)" : "%1$s (nimi on muudetud)",
+ "renamed file" : "muudetud nimega fail",
"\"%1$s\" is a forbidden file or folder name." : "„%1$s“ on keelatud faili- või kaustanimi.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "„%1$s“ on keelatud faili- või kaustanime eesliide.",
"\"%1$s\" is not allowed inside a file or folder name." : "„%1$s“ pole faili- või kaustanimes lubatud.",
diff --git a/lib/l10n/et_EE.json b/lib/l10n/et_EE.json
index 99c9583bf87..65621b2643a 100644
--- a/lib/l10n/et_EE.json
+++ b/lib/l10n/et_EE.json
@@ -82,6 +82,8 @@
"Destination does not exist" : "Sihtmeediat pole olemas",
"Destination is not creatable" : "Sihtmeedia pole loodav",
"Dot files are not allowed" : "Punktiga failid pole lubatud",
+ "%1$s (renamed)" : "%1$s (nimi on muudetud)",
+ "renamed file" : "muudetud nimega fail",
"\"%1$s\" is a forbidden file or folder name." : "„%1$s“ on keelatud faili- või kaustanimi.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "„%1$s“ on keelatud faili- või kaustanime eesliide.",
"\"%1$s\" is not allowed inside a file or folder name." : "„%1$s“ pole faili- või kaustanimes lubatud.",
diff --git a/lib/l10n/ga.js b/lib/l10n/ga.js
index 9b05143b101..807a668847e 100644
--- a/lib/l10n/ga.js
+++ b/lib/l10n/ga.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "Níl ceann scríbe ann",
"Destination is not creatable" : "Níl ceann scríbe cruthaithe",
"Dot files are not allowed" : "Ní cheadaítear comhaid ponc",
+ "%1$s (renamed)" : "%1$s (athainmnithe)",
+ "renamed file" : "comhad athainmnithe",
"\"%1$s\" is a forbidden file or folder name." : "Is ainm toirmiscthe comhaid nó fillteáin é \"%1$s\".",
"\"%1$s\" is a forbidden prefix for file or folder names." : "Réimír toirmiscthe é \"%1$s\" d'ainmneacha comhaid nó fillteán.",
"\"%1$s\" is not allowed inside a file or folder name." : "Ní cheadaítear \"%1$s\" taobh istigh d'ainm comhaid nó fillteáin.",
diff --git a/lib/l10n/ga.json b/lib/l10n/ga.json
index ee093dac05e..657ef31f4e3 100644
--- a/lib/l10n/ga.json
+++ b/lib/l10n/ga.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "Níl ceann scríbe ann",
"Destination is not creatable" : "Níl ceann scríbe cruthaithe",
"Dot files are not allowed" : "Ní cheadaítear comhaid ponc",
+ "%1$s (renamed)" : "%1$s (athainmnithe)",
+ "renamed file" : "comhad athainmnithe",
"\"%1$s\" is a forbidden file or folder name." : "Is ainm toirmiscthe comhaid nó fillteáin é \"%1$s\".",
"\"%1$s\" is a forbidden prefix for file or folder names." : "Réimír toirmiscthe é \"%1$s\" d'ainmneacha comhaid nó fillteán.",
"\"%1$s\" is not allowed inside a file or folder name." : "Ní cheadaítear \"%1$s\" taobh istigh d'ainm comhaid nó fillteáin.",
diff --git a/lib/l10n/it.js b/lib/l10n/it.js
index 50750f18726..33a2c8ad6bb 100644
--- a/lib/l10n/it.js
+++ b/lib/l10n/it.js
@@ -82,6 +82,8 @@ OC.L10N.register(
"Module with ID: %s does not exist. Please enable it in your apps settings or contact your administrator." : "Il modulo con ID: %s non esiste. Abilitalo nelle impostazioni delle applicazioni o contatta il tuo amministratore.",
"File is too large to convert" : "Il file è troppo grande per essere convertito",
"Dot files are not allowed" : "I file con un punto iniziale non sono consentiti",
+ "%1$s (renamed)" : "%1$s (rinominato)",
+ "renamed file" : "file rinominato",
"File already exists" : "Il file esiste già",
"Invalid path" : "Percorso non valido",
"Failed to create file from template" : "Impossibile creare un file dal modello",
diff --git a/lib/l10n/it.json b/lib/l10n/it.json
index c6a820d0f5d..4cd53fbed0a 100644
--- a/lib/l10n/it.json
+++ b/lib/l10n/it.json
@@ -80,6 +80,8 @@
"Module with ID: %s does not exist. Please enable it in your apps settings or contact your administrator." : "Il modulo con ID: %s non esiste. Abilitalo nelle impostazioni delle applicazioni o contatta il tuo amministratore.",
"File is too large to convert" : "Il file è troppo grande per essere convertito",
"Dot files are not allowed" : "I file con un punto iniziale non sono consentiti",
+ "%1$s (renamed)" : "%1$s (rinominato)",
+ "renamed file" : "file rinominato",
"File already exists" : "Il file esiste già",
"Invalid path" : "Percorso non valido",
"Failed to create file from template" : "Impossibile creare un file dal modello",
diff --git a/lib/l10n/pl.js b/lib/l10n/pl.js
index 0d9fd0cb98a..953682de0ab 100644
--- a/lib/l10n/pl.js
+++ b/lib/l10n/pl.js
@@ -82,6 +82,8 @@ OC.L10N.register(
"Empty file" : "Pusty plik",
"Module with ID: %s does not exist. Please enable it in your apps settings or contact your administrator." : "Moduł o ID: %s nie istnieje. Włącz go w ustawieniach aplikacji lub skontaktuj się z administratorem.",
"Dot files are not allowed" : "Pliki z kropką są niedozwolone",
+ "%1$s (renamed)" : "%1$s (zmieniona nazwa)",
+ "renamed file" : "zmieniona nazwa pliku",
"Invalid parent path" : "Nieprawidłowa ścieżka nadrzędna",
"File already exists" : "Plik już istnieje",
"Invalid path" : "Niewłaściwa ścieżka",
diff --git a/lib/l10n/pl.json b/lib/l10n/pl.json
index c97634e8eff..4edf90eedba 100644
--- a/lib/l10n/pl.json
+++ b/lib/l10n/pl.json
@@ -80,6 +80,8 @@
"Empty file" : "Pusty plik",
"Module with ID: %s does not exist. Please enable it in your apps settings or contact your administrator." : "Moduł o ID: %s nie istnieje. Włącz go w ustawieniach aplikacji lub skontaktuj się z administratorem.",
"Dot files are not allowed" : "Pliki z kropką są niedozwolone",
+ "%1$s (renamed)" : "%1$s (zmieniona nazwa)",
+ "renamed file" : "zmieniona nazwa pliku",
"Invalid parent path" : "Nieprawidłowa ścieżka nadrzędna",
"File already exists" : "Plik już istnieje",
"Invalid path" : "Niewłaściwa ścieżka",
diff --git a/lib/l10n/pt_BR.js b/lib/l10n/pt_BR.js
index 975a321f27c..bf7f7728be6 100644
--- a/lib/l10n/pt_BR.js
+++ b/lib/l10n/pt_BR.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "Destino não existe",
"Destination is not creatable" : "Destino não pode ser criado",
"Dot files are not allowed" : "Arquivos Dot não são permitidos",
+ "%1$s (renamed)" : "%1$s (renomeado)",
+ "renamed file" : "arquivo renomeado",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" é um nome de arquivo ou pasta proibido.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" é um prefixo proibido para nomes de arquivos ou pastas.",
"\"%1$s\" is not allowed inside a file or folder name." : "\"%1$s\" não é permitido dentro de um nome de arquivo ou pasta.",
@@ -141,7 +143,7 @@ OC.L10N.register(
"Profile picture" : "Foto do perfil",
"About" : "Sobre",
"Display name" : "Nome de exibição",
- "Headline" : "Título ",
+ "Headline" : "Título",
"Organisation" : "Organização",
"Role" : "Função",
"Pronouns" : "Pronomes",
@@ -273,7 +275,7 @@ OC.L10N.register(
"A valid Login must be provided" : "Um Login válido deve ser fornecido",
"Login contains whitespace at the beginning or at the end" : "O login contém espaços em branco no início ou no final",
"Login must not consist of dots only" : "O login não deve consistir apenas de pontos",
- "Login is too long" : "O login é muito longo",
+ "Login is too long" : "Login é muito longo",
"Login is invalid because files already exist for this user" : "O login é inválido porque já existem arquivos para este usuário",
"Account disabled" : "Conta desativada",
"Login canceled by app" : "Login cancelado pelo aplicativo",
diff --git a/lib/l10n/pt_BR.json b/lib/l10n/pt_BR.json
index 56506c4cce0..ad7df10df2b 100644
--- a/lib/l10n/pt_BR.json
+++ b/lib/l10n/pt_BR.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "Destino não existe",
"Destination is not creatable" : "Destino não pode ser criado",
"Dot files are not allowed" : "Arquivos Dot não são permitidos",
+ "%1$s (renamed)" : "%1$s (renomeado)",
+ "renamed file" : "arquivo renomeado",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" é um nome de arquivo ou pasta proibido.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" é um prefixo proibido para nomes de arquivos ou pastas.",
"\"%1$s\" is not allowed inside a file or folder name." : "\"%1$s\" não é permitido dentro de um nome de arquivo ou pasta.",
@@ -139,7 +141,7 @@
"Profile picture" : "Foto do perfil",
"About" : "Sobre",
"Display name" : "Nome de exibição",
- "Headline" : "Título ",
+ "Headline" : "Título",
"Organisation" : "Organização",
"Role" : "Função",
"Pronouns" : "Pronomes",
@@ -271,7 +273,7 @@
"A valid Login must be provided" : "Um Login válido deve ser fornecido",
"Login contains whitespace at the beginning or at the end" : "O login contém espaços em branco no início ou no final",
"Login must not consist of dots only" : "O login não deve consistir apenas de pontos",
- "Login is too long" : "O login é muito longo",
+ "Login is too long" : "Login é muito longo",
"Login is invalid because files already exist for this user" : "O login é inválido porque já existem arquivos para este usuário",
"Account disabled" : "Conta desativada",
"Login canceled by app" : "Login cancelado pelo aplicativo",
diff --git a/lib/l10n/sr.js b/lib/l10n/sr.js
index b62a808994d..6bbd5d62333 100644
--- a/lib/l10n/sr.js
+++ b/lib/l10n/sr.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "Одредиште не постоји",
"Destination is not creatable" : "Одредиште не може да се креира",
"Dot files are not allowed" : "Фајлови са почетном тачком нису дозвољени",
+ "%1$s (renamed)" : "%1$s (преименован)",
+ "renamed file" : "преименован фајл",
"\"%1$s\" is a forbidden file or folder name." : "„%1$s” је забрањено име фајла или фолдера.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "„%1$s” је забрањени префикс имена фајла или фолдера.",
"\"%1$s\" is not allowed inside a file or folder name." : "„%1$s” није дозвољено у имену фајла или фолдера.",
diff --git a/lib/l10n/sr.json b/lib/l10n/sr.json
index 7dbc69c583a..8d6b3cc72c3 100644
--- a/lib/l10n/sr.json
+++ b/lib/l10n/sr.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "Одредиште не постоји",
"Destination is not creatable" : "Одредиште не може да се креира",
"Dot files are not allowed" : "Фајлови са почетном тачком нису дозвољени",
+ "%1$s (renamed)" : "%1$s (преименован)",
+ "renamed file" : "преименован фајл",
"\"%1$s\" is a forbidden file or folder name." : "„%1$s” је забрањено име фајла или фолдера.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "„%1$s” је забрањени префикс имена фајла или фолдера.",
"\"%1$s\" is not allowed inside a file or folder name." : "„%1$s” није дозвољено у имену фајла или фолдера.",
diff --git a/lib/l10n/sv.js b/lib/l10n/sv.js
index ed4c4af3ef0..f203a0471e7 100644
--- a/lib/l10n/sv.js
+++ b/lib/l10n/sv.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "Destinationen finns inte",
"Destination is not creatable" : "Destinationen går inte att skapa",
"Dot files are not allowed" : "Dot-filer är inte tillåtna",
+ "%1$s (renamed)" : "%1$s (omdöpt)",
+ "renamed file" : "omdöpt fil",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" är ett förbjudet fil- eller mappnamn.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" är ett förbjudet prefix för fil- eller mappnamn.",
"\"%1$s\" is not allowed inside a file or folder name." : "\"%1$s\" är inte tillåtet i ett fil- eller mappnamn.",
diff --git a/lib/l10n/sv.json b/lib/l10n/sv.json
index 55855426f34..3f3db6805e8 100644
--- a/lib/l10n/sv.json
+++ b/lib/l10n/sv.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "Destinationen finns inte",
"Destination is not creatable" : "Destinationen går inte att skapa",
"Dot files are not allowed" : "Dot-filer är inte tillåtna",
+ "%1$s (renamed)" : "%1$s (omdöpt)",
+ "renamed file" : "omdöpt fil",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" är ett förbjudet fil- eller mappnamn.",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" är ett förbjudet prefix för fil- eller mappnamn.",
"\"%1$s\" is not allowed inside a file or folder name." : "\"%1$s\" är inte tillåtet i ett fil- eller mappnamn.",
diff --git a/lib/l10n/zh_CN.js b/lib/l10n/zh_CN.js
index 1637350f1e9..0cc4fd8d378 100644
--- a/lib/l10n/zh_CN.js
+++ b/lib/l10n/zh_CN.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "目标不存在",
"Destination is not creatable" : "目标不可创建",
"Dot files are not allowed" : "以 . 开头的文件不被允许",
+ "%1$s (renamed)" : "%1$s(已重命名)",
+ "renamed file" : "已重命名文件",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" 是禁止的文件或文件夹名称。",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" 是文件或文件夹名称的禁止前缀。",
"\"%1$s\" is not allowed inside a file or folder name." : "文件或文件夹名称中不允许出现 \"%1$s\"。",
diff --git a/lib/l10n/zh_CN.json b/lib/l10n/zh_CN.json
index dd94f1bb5cf..2ba31a10e87 100644
--- a/lib/l10n/zh_CN.json
+++ b/lib/l10n/zh_CN.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "目标不存在",
"Destination is not creatable" : "目标不可创建",
"Dot files are not allowed" : "以 . 开头的文件不被允许",
+ "%1$s (renamed)" : "%1$s(已重命名)",
+ "renamed file" : "已重命名文件",
"\"%1$s\" is a forbidden file or folder name." : "\"%1$s\" 是禁止的文件或文件夹名称。",
"\"%1$s\" is a forbidden prefix for file or folder names." : "\"%1$s\" 是文件或文件夹名称的禁止前缀。",
"\"%1$s\" is not allowed inside a file or folder name." : "文件或文件夹名称中不允许出现 \"%1$s\"。",
diff --git a/lib/l10n/zh_HK.js b/lib/l10n/zh_HK.js
index a85c29e400c..b4bb06b4cdc 100644
--- a/lib/l10n/zh_HK.js
+++ b/lib/l10n/zh_HK.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "目的地不存在",
"Destination is not creatable" : "無法建立目的地",
"Dot files are not allowed" : "不允許小數點開頭的檔案",
+ "%1$s (renamed)" : "%1$s(已重新命名)",
+ "renamed file" : "已重新命名的檔案",
"\"%1$s\" is a forbidden file or folder name." : "「%1$s」是禁止的檔案或資料夾名稱。",
"\"%1$s\" is a forbidden prefix for file or folder names." : "「%1$s」是禁止的檔案或資料夾名稱前綴。",
"\"%1$s\" is not allowed inside a file or folder name." : "「%1$s」不允許出現在檔案或資料夾名稱中。",
diff --git a/lib/l10n/zh_HK.json b/lib/l10n/zh_HK.json
index b58db1e510c..6cc1edd0f35 100644
--- a/lib/l10n/zh_HK.json
+++ b/lib/l10n/zh_HK.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "目的地不存在",
"Destination is not creatable" : "無法建立目的地",
"Dot files are not allowed" : "不允許小數點開頭的檔案",
+ "%1$s (renamed)" : "%1$s(已重新命名)",
+ "renamed file" : "已重新命名的檔案",
"\"%1$s\" is a forbidden file or folder name." : "「%1$s」是禁止的檔案或資料夾名稱。",
"\"%1$s\" is a forbidden prefix for file or folder names." : "「%1$s」是禁止的檔案或資料夾名稱前綴。",
"\"%1$s\" is not allowed inside a file or folder name." : "「%1$s」不允許出現在檔案或資料夾名稱中。",
diff --git a/lib/l10n/zh_TW.js b/lib/l10n/zh_TW.js
index 4f92a865290..016689524c5 100644
--- a/lib/l10n/zh_TW.js
+++ b/lib/l10n/zh_TW.js
@@ -93,6 +93,8 @@ OC.L10N.register(
"Destination does not exist" : "目的地不存在",
"Destination is not creatable" : "無法建立目的地",
"Dot files are not allowed" : "不允許小數點開頭的檔案",
+ "%1$s (renamed)" : "%1$s(已重新命名)",
+ "renamed file" : "已重新命名檔案",
"\"%1$s\" is a forbidden file or folder name." : "「%1$s」是禁止的檔案或資料夾名稱。",
"\"%1$s\" is a forbidden prefix for file or folder names." : "「%1$s」是禁止的檔案或資料夾名稱前綴。",
"\"%1$s\" is not allowed inside a file or folder name." : "「%1$s」不允許出現在檔案或資料夾名稱中。",
diff --git a/lib/l10n/zh_TW.json b/lib/l10n/zh_TW.json
index 34b32540bc8..67f95c65e75 100644
--- a/lib/l10n/zh_TW.json
+++ b/lib/l10n/zh_TW.json
@@ -91,6 +91,8 @@
"Destination does not exist" : "目的地不存在",
"Destination is not creatable" : "無法建立目的地",
"Dot files are not allowed" : "不允許小數點開頭的檔案",
+ "%1$s (renamed)" : "%1$s(已重新命名)",
+ "renamed file" : "已重新命名檔案",
"\"%1$s\" is a forbidden file or folder name." : "「%1$s」是禁止的檔案或資料夾名稱。",
"\"%1$s\" is a forbidden prefix for file or folder names." : "「%1$s」是禁止的檔案或資料夾名稱前綴。",
"\"%1$s\" is not allowed inside a file or folder name." : "「%1$s」不允許出現在檔案或資料夾名稱中。",
diff --git a/lib/private/Accounts/AccountManager.php b/lib/private/Accounts/AccountManager.php
index d69e72a29de..e8b67311636 100644
--- a/lib/private/Accounts/AccountManager.php
+++ b/lib/private/Accounts/AccountManager.php
@@ -131,9 +131,7 @@ class AccountManager implements IAccountManager {
$property->setScope(self::SCOPE_LOCAL);
}
} else {
- // migrate scope values to the new format
- // invalid scopes are mapped to a default value
- $property->setScope(AccountProperty::mapScopeToV2($property->getScope()));
+ $property->setScope($property->getScope());
}
}
diff --git a/lib/private/Accounts/AccountProperty.php b/lib/private/Accounts/AccountProperty.php
index 0c4ad568709..3a89e9bbc7a 100644
--- a/lib/private/Accounts/AccountProperty.php
+++ b/lib/private/Accounts/AccountProperty.php
@@ -55,16 +55,11 @@ class AccountProperty implements IAccountProperty {
* @since 15.0.0
*/
public function setScope(string $scope): IAccountProperty {
- $newScope = $this->mapScopeToV2($scope);
- if (!in_array($newScope, [
- IAccountManager::SCOPE_LOCAL,
- IAccountManager::SCOPE_FEDERATED,
- IAccountManager::SCOPE_PRIVATE,
- IAccountManager::SCOPE_PUBLISHED
- ])) {
+ if (!in_array($scope, IAccountManager::ALLOWED_SCOPES, )) {
throw new InvalidArgumentException('Invalid scope');
}
- $this->scope = $newScope;
+ /** @var IAccountManager::SCOPE_* $scope */
+ $this->scope = $scope;
return $this;
}
@@ -105,19 +100,6 @@ class AccountProperty implements IAccountProperty {
return $this->scope;
}
- public static function mapScopeToV2(string $scope): string {
- if (str_starts_with($scope, 'v2-')) {
- return $scope;
- }
-
- return match ($scope) {
- IAccountManager::VISIBILITY_PRIVATE, '' => IAccountManager::SCOPE_LOCAL,
- IAccountManager::VISIBILITY_CONTACTS_ONLY => IAccountManager::SCOPE_FEDERATED,
- IAccountManager::VISIBILITY_PUBLIC => IAccountManager::SCOPE_PUBLISHED,
- default => $scope,
- };
- }
-
/**
* Get the verification status of a property
*
diff --git a/lib/private/AppFramework/Bootstrap/Coordinator.php b/lib/private/AppFramework/Bootstrap/Coordinator.php
index 2b04d291730..4e613703dec 100644
--- a/lib/private/AppFramework/Bootstrap/Coordinator.php
+++ b/lib/private/AppFramework/Bootstrap/Coordinator.php
@@ -83,11 +83,12 @@ class Coordinator {
$appNameSpace = App::buildAppNamespace($appId);
$applicationClassName = $appNameSpace . '\\AppInfo\\Application';
try {
- if (class_exists($applicationClassName) && in_array(IBootstrap::class, class_implements($applicationClassName), true)) {
+ if (class_exists($applicationClassName) && is_a($applicationClassName, IBootstrap::class, true)) {
$this->eventLogger->start("bootstrap:register_app:$appId:application", "Load `Application` instance for $appId");
try {
- /** @var IBootstrap|App $application */
- $apps[$appId] = $application = $this->serverContainer->query($applicationClassName);
+ /** @var IBootstrap&App $application */
+ $application = $this->serverContainer->query($applicationClassName);
+ $apps[$appId] = $application;
} catch (QueryException $e) {
// Weird, but ok
$this->eventLogger->end("bootstrap:register_app:$appId");
diff --git a/lib/private/AppFramework/Utility/SimpleContainer.php b/lib/private/AppFramework/Utility/SimpleContainer.php
index 24918992ea3..9af65a37ab8 100644
--- a/lib/private/AppFramework/Utility/SimpleContainer.php
+++ b/lib/private/AppFramework/Utility/SimpleContainer.php
@@ -153,13 +153,13 @@ class SimpleContainer implements ArrayAccess, ContainerInterface, IContainer {
return $closure($this);
};
$name = $this->sanitizeName($name);
- if (isset($this[$name])) {
- unset($this[$name]);
+ if (isset($this->container[$name])) {
+ unset($this->container[$name]);
}
if ($shared) {
- $this[$name] = $wrapped;
+ $this->container[$name] = $wrapped;
} else {
- $this[$name] = $this->container->factory($wrapped);
+ $this->container[$name] = $this->container->factory($wrapped);
}
}
diff --git a/lib/private/Calendar/Manager.php b/lib/private/Calendar/Manager.php
index e86e0e1d410..21370e74d54 100644
--- a/lib/private/Calendar/Manager.php
+++ b/lib/private/Calendar/Manager.php
@@ -33,6 +33,7 @@ use Sabre\HTTP\Response;
use Sabre\VObject\Component\VCalendar;
use Sabre\VObject\Component\VEvent;
use Sabre\VObject\Component\VFreeBusy;
+use Sabre\VObject\ParseException;
use Sabre\VObject\Property\VCard\DateTime;
use Sabre\VObject\Reader;
use Throwable;
@@ -235,9 +236,14 @@ class Manager implements IManager {
$this->logger->warning('iMip message could not be processed because user has no calendars');
return false;
}
-
- /** @var VCalendar $vObject|null */
- $calendarObject = Reader::read($calendarData);
+
+ try {
+ /** @var VCalendar $vObject|null */
+ $calendarObject = Reader::read($calendarData);
+ } catch (ParseException $e) {
+ $this->logger->error('iMip message could not be processed because an error occurred while parsing the iMip message', ['exception' => $e]);
+ return false;
+ }
if (!isset($calendarObject->METHOD) || $calendarObject->METHOD->getValue() !== 'REQUEST') {
$this->logger->warning('iMip message contains an incorrect or invalid method');
@@ -249,6 +255,7 @@ class Manager implements IManager {
return false;
}
+ /** @var VEvent|null $vEvent */
$eventObject = $calendarObject->VEVENT;
if (!isset($eventObject->UID)) {
@@ -256,6 +263,11 @@ class Manager implements IManager {
return false;
}
+ if (!isset($eventObject->ORGANIZER)) {
+ $this->logger->warning('iMip message event dose not contains an organizer');
+ return false;
+ }
+
if (!isset($eventObject->ATTENDEE)) {
$this->logger->warning('iMip message event dose not contains any attendees');
return false;
@@ -296,7 +308,7 @@ class Manager implements IManager {
}
}
- $this->logger->warning('iMip message event could not be processed because the no corresponding event was found in any calendar');
+ $this->logger->warning('iMip message event could not be processed because no corresponding event was found in any calendar');
return false;
}
@@ -309,23 +321,51 @@ class Manager implements IManager {
string $recipient,
string $calendarData,
): bool {
- /** @var VCalendar $vObject|null */
- $vObject = Reader::read($calendarData);
+
+ $calendars = $this->getCalendarsForPrincipal($principalUri);
+ if (empty($calendars)) {
+ $this->logger->warning('iMip message could not be processed because user has no calendars');
+ return false;
+ }
+
+ try {
+ /** @var VCalendar $vObject|null */
+ $vObject = Reader::read($calendarData);
+ } catch (ParseException $e) {
+ $this->logger->error('iMip message could not be processed because an error occurred while parsing the iMip message', ['exception' => $e]);
+ return false;
+ }
if ($vObject === null) {
+ $this->logger->warning('iMip message contains an invalid calendar object');
+ return false;
+ }
+
+ if (!isset($vObject->METHOD) || $vObject->METHOD->getValue() !== 'REPLY') {
+ $this->logger->warning('iMip message contains an incorrect or invalid method');
+ return false;
+ }
+
+ if (!isset($vObject->VEVENT)) {
+ $this->logger->warning('iMip message contains no event');
return false;
}
/** @var VEvent|null $vEvent */
- $vEvent = $vObject->{'VEVENT'};
+ $vEvent = $vObject->VEVENT;
+
+ if (!isset($vEvent->UID)) {
+ $this->logger->warning('iMip message event dose not contains a UID');
+ return false;
+ }
- if ($vEvent === null) {
+ if (!isset($vEvent->ORGANIZER)) {
+ $this->logger->warning('iMip message event dose not contains an organizer');
return false;
}
- // First, we check if the correct method is passed to us
- if (strcasecmp('REPLY', $vObject->{'METHOD'}->getValue()) !== 0) {
- $this->logger->warning('Wrong method provided for processing');
+ if (!isset($vEvent->ATTENDEE)) {
+ $this->logger->warning('iMip message event dose not contains any attendees');
return false;
}
@@ -333,7 +373,7 @@ class Manager implements IManager {
$organizer = substr($vEvent->{'ORGANIZER'}->getValue(), 7);
if (strcasecmp($recipient, $organizer) !== 0) {
- $this->logger->warning('Recipient and ORGANIZER must be identical');
+ $this->logger->warning('iMip message event could not be processed because recipient and ORGANIZER must be identical');
return false;
}
@@ -341,13 +381,7 @@ class Manager implements IManager {
/** @var DateTime $eventTime */
$eventTime = $vEvent->{'DTSTART'};
if ($eventTime->getDateTime()->getTimeStamp() < $this->timeFactory->getTime()) { // this might cause issues with recurrences
- $this->logger->warning('Only events in the future are processed');
- return false;
- }
-
- $calendars = $this->getCalendarsForPrincipal($principalUri);
- if (empty($calendars)) {
- $this->logger->warning('Could not find any calendars for principal ' . $principalUri);
+ $this->logger->warning('iMip message event could not be processed because the event is in the past');
return false;
}
@@ -369,14 +403,14 @@ class Manager implements IManager {
}
if (empty($found)) {
- $this->logger->info('Event not found in any calendar for principal ' . $principalUri . 'and UID' . $vEvent->{'UID'}->getValue());
+ $this->logger->warning('iMip message event could not be processed because no corresponding event was found in any calendar ' . $principalUri . 'and UID' . $vEvent->{'UID'}->getValue());
return false;
}
try {
$found->handleIMipMessage($name, $calendarData); // sabre will handle the scheduling behind the scenes
} catch (CalendarException $e) {
- $this->logger->error('Could not update calendar for iMIP processing', ['exception' => $e]);
+ $this->logger->error('An error occurred while processing the iMip message event', ['exception' => $e]);
return false;
}
return true;
@@ -393,29 +427,57 @@ class Manager implements IManager {
string $recipient,
string $calendarData,
): bool {
- /** @var VCalendar $vObject|null */
- $vObject = Reader::read($calendarData);
+
+ $calendars = $this->getCalendarsForPrincipal($principalUri);
+ if (empty($calendars)) {
+ $this->logger->warning('iMip message could not be processed because user has no calendars');
+ return false;
+ }
+
+ try {
+ /** @var VCalendar $vObject|null */
+ $vObject = Reader::read($calendarData);
+ } catch (ParseException $e) {
+ $this->logger->error('iMip message could not be processed because an error occurred while parsing the iMip message', ['exception' => $e]);
+ return false;
+ }
if ($vObject === null) {
+ $this->logger->warning('iMip message contains an invalid calendar object');
+ return false;
+ }
+
+ if (!isset($vObject->METHOD) || $vObject->METHOD->getValue() !== 'CANCEL') {
+ $this->logger->warning('iMip message contains an incorrect or invalid method');
+ return false;
+ }
+
+ if (!isset($vObject->VEVENT)) {
+ $this->logger->warning('iMip message contains no event');
return false;
}
/** @var VEvent|null $vEvent */
$vEvent = $vObject->{'VEVENT'};
- if ($vEvent === null) {
+ if (!isset($vEvent->UID)) {
+ $this->logger->warning('iMip message event dose not contains a UID');
+ return false;
+ }
+
+ if (!isset($vEvent->ORGANIZER)) {
+ $this->logger->warning('iMip message event dose not contains an organizer');
return false;
}
- // First, we check if the correct method is passed to us
- if (strcasecmp('CANCEL', $vObject->{'METHOD'}->getValue()) !== 0) {
- $this->logger->warning('Wrong method provided for processing');
+ if (!isset($vEvent->ATTENDEE)) {
+ $this->logger->warning('iMip message event dose not contains any attendees');
return false;
}
$attendee = substr($vEvent->{'ATTENDEE'}->getValue(), 7);
if (strcasecmp($recipient, $attendee) !== 0) {
- $this->logger->warning('Recipient must be an ATTENDEE of this event');
+ $this->logger->warning('iMip message event could not be processed because recipient must be an ATTENDEE of this event');
return false;
}
@@ -426,7 +488,7 @@ class Manager implements IManager {
$organizer = substr($vEvent->{'ORGANIZER'}->getValue(), 7);
$isNotOrganizer = ($replyTo !== null) ? (strcasecmp($sender, $organizer) !== 0 && strcasecmp($replyTo, $organizer) !== 0) : (strcasecmp($sender, $organizer) !== 0);
if ($isNotOrganizer) {
- $this->logger->warning('Sender must be the ORGANIZER of this event');
+ $this->logger->warning('iMip message event could not be processed because sender must be the ORGANIZER of this event');
return false;
}
@@ -434,14 +496,7 @@ class Manager implements IManager {
/** @var DateTime $eventTime */
$eventTime = $vEvent->{'DTSTART'};
if ($eventTime->getDateTime()->getTimeStamp() < $this->timeFactory->getTime()) { // this might cause issues with recurrences
- $this->logger->warning('Only events in the future are processed');
- return false;
- }
-
- // Check if we have a calendar to work with
- $calendars = $this->getCalendarsForPrincipal($principalUri);
- if (empty($calendars)) {
- $this->logger->warning('Could not find any calendars for principal ' . $principalUri);
+ $this->logger->warning('iMip message event could not be processed because the event is in the past');
return false;
}
@@ -463,17 +518,15 @@ class Manager implements IManager {
}
if (empty($found)) {
- $this->logger->info('Event not found in any calendar for principal ' . $principalUri . 'and UID' . $vEvent->{'UID'}->getValue());
- // this is a safe operation
- // we can ignore events that have been cancelled but were not in the calendar anyway
- return true;
+ $this->logger->warning('iMip message event could not be processed because no corresponding event was found in any calendar ' . $principalUri . 'and UID' . $vEvent->{'UID'}->getValue());
+ return false;
}
try {
$found->handleIMipMessage($name, $calendarData); // sabre will handle the scheduling behind the scenes
return true;
} catch (CalendarException $e) {
- $this->logger->error('Could not update calendar for iMIP processing', ['exception' => $e]);
+ $this->logger->error('An error occurred while processing the iMip message event', ['exception' => $e]);
return false;
}
}
diff --git a/lib/private/DB/Adapter.php b/lib/private/DB/Adapter.php
index 8f1b8e6d75f..edd8c1bf023 100644
--- a/lib/private/DB/Adapter.php
+++ b/lib/private/DB/Adapter.php
@@ -28,11 +28,25 @@ class Adapter {
/**
* @param string $table name
*
- * @return int id of last insert statement
+ * @return int id of last insert statement, 0 in case there was no INSERT before or it failed to get the ID
* @throws Exception
*/
- public function lastInsertId($table) {
- return (int)$this->conn->realLastInsertId($table);
+ public function lastInsertId($table, bool $allowRetry = true): int {
+ $return = $this->conn->realLastInsertId($table);
+ if ($return === 0 && $allowRetry) {
+ /**
+ * During a reconnect we are losing the connection and when the
+ * realLastInsertId call is the one triggering the reconnect, it
+ * does not return the ID. But inside the reconnect, we were able
+ * to save the last insert id, so calling it a second time is going
+ * to be successful.
+ * We can not return the result on the initial call, as we are already
+ * way deeper in the stack performing the actual database query on
+ * the doctrine driver.
+ */
+ return $this->lastInsertId($table, false);
+ }
+ return $return;
}
/**
diff --git a/lib/private/DB/AdapterOCI8.php b/lib/private/DB/AdapterOCI8.php
index 0a509090bca..f5ad9f7c934 100644
--- a/lib/private/DB/AdapterOCI8.php
+++ b/lib/private/DB/AdapterOCI8.php
@@ -8,7 +8,7 @@
namespace OC\DB;
class AdapterOCI8 extends Adapter {
- public function lastInsertId($table) {
+ public function lastInsertId($table, bool $allowRetry = true): int {
if (is_null($table)) {
throw new \InvalidArgumentException('Oracle requires a table name to be passed into lastInsertId()');
}
diff --git a/lib/private/DB/AdapterPgSql.php b/lib/private/DB/AdapterPgSql.php
index db48c81c2c5..b321fcf4715 100644
--- a/lib/private/DB/AdapterPgSql.php
+++ b/lib/private/DB/AdapterPgSql.php
@@ -9,7 +9,7 @@ namespace OC\DB;
class AdapterPgSql extends Adapter {
- public function lastInsertId($table) {
+ public function lastInsertId($table, bool $allowRetry = true): int {
$result = $this->conn->executeQuery('SELECT lastval()');
$val = $result->fetchOne();
$result->free();
diff --git a/lib/private/DB/Connection.php b/lib/private/DB/Connection.php
index 96dd578b2ef..4ba2d2a341d 100644
--- a/lib/private/DB/Connection.php
+++ b/lib/private/DB/Connection.php
@@ -92,6 +92,8 @@ class Connection extends PrimaryReadReplicaConnection {
protected ShardConnectionManager $shardConnectionManager;
protected AutoIncrementHandler $autoIncrementHandler;
protected bool $isShardingEnabled;
+ protected bool $disableReconnect = false;
+ protected int $lastInsertId = 0;
public const SHARD_PRESETS = [
'filecache' => [
@@ -510,9 +512,9 @@ class Connection extends PrimaryReadReplicaConnection {
* because the underlying database may not even support the notion of AUTO_INCREMENT/IDENTITY
* columns or sequences.
*
- * @param string $seqName Name of the sequence object from which the ID should be returned.
+ * @param ?string $name Name of the sequence object from which the ID should be returned.
*
- * @return int the last inserted ID.
+ * @return int the last inserted ID, 0 in case there was no INSERT before or it failed to get the ID
* @throws Exception
*/
public function lastInsertId($name = null): int {
@@ -526,8 +528,13 @@ class Connection extends PrimaryReadReplicaConnection {
* @internal
* @throws Exception
*/
- public function realLastInsertId($seqName = null) {
- return parent::lastInsertId($seqName);
+ public function realLastInsertId($seqName = null): int {
+ if ($this->lastInsertId !== 0) {
+ $lastInsertId = $this->lastInsertId;
+ $this->lastInsertId = 0;
+ return $lastInsertId;
+ }
+ return (int)parent::lastInsertId($seqName);
}
/**
@@ -896,11 +903,23 @@ class Connection extends PrimaryReadReplicaConnection {
if (
!isset($this->lastConnectionCheck[$this->getConnectionName()]) ||
time() <= $this->lastConnectionCheck[$this->getConnectionName()] + 30 ||
- $this->isTransactionActive()
+ $this->isTransactionActive() ||
+ $this->disableReconnect
) {
return;
}
+ if ($this->getDatabaseProvider() === IDBConnection::PLATFORM_MYSQL) {
+ /**
+ * Before reconnecting we save the lastInsertId, so that if the reconnect
+ * happens between the INSERT executeStatement() and the getLastInsertId call
+ * we are able to return the correct result after all.
+ */
+ $this->disableReconnect = true;
+ $this->lastInsertId = (int)parent::lastInsertId();
+ $this->disableReconnect = false;
+ }
+
try {
$this->_conn->query($this->getDriver()->getDatabasePlatform()->getDummySelectSQL());
$this->lastConnectionCheck[$this->getConnectionName()] = time();
diff --git a/lib/private/Encryption/EncryptionEventListener.php b/lib/private/Encryption/EncryptionEventListener.php
new file mode 100644
index 00000000000..59ac0dea932
--- /dev/null
+++ b/lib/private/Encryption/EncryptionEventListener.php
@@ -0,0 +1,93 @@
+<?php
+
+declare(strict_types=1);
+
+/**
+ * SPDX-FileCopyrightText: 2024 Nextcloud GmbH and Nextcloud contributors
+ * SPDX-License-Identifier: AGPL-3.0-only
+ */
+
+namespace OC\Encryption;
+
+use OC\Files\SetupManager;
+use OC\Files\View;
+use OCA\Files_Trashbin\Events\NodeRestoredEvent;
+use OCP\Encryption\IFile;
+use OCP\EventDispatcher\Event;
+use OCP\EventDispatcher\IEventDispatcher;
+use OCP\EventDispatcher\IEventListener;
+use OCP\Files\Events\Node\NodeRenamedEvent;
+use OCP\IUser;
+use OCP\IUserSession;
+use OCP\Share\Events\ShareCreatedEvent;
+use OCP\Share\Events\ShareDeletedEvent;
+use Psr\Log\LoggerInterface;
+
+/** @template-implements IEventListener<NodeRenamedEvent|ShareCreatedEvent|ShareDeletedEvent|NodeRestoredEvent> */
+class EncryptionEventListener implements IEventListener {
+ private ?Update $updater = null;
+
+ public function __construct(
+ private IUserSession $userSession,
+ private SetupManager $setupManager,
+ private Manager $encryptionManager,
+ ) {
+ }
+
+ public static function register(IEventDispatcher $dispatcher): void {
+ $dispatcher->addServiceListener(NodeRenamedEvent::class, static::class);
+ $dispatcher->addServiceListener(ShareCreatedEvent::class, static::class);
+ $dispatcher->addServiceListener(ShareDeletedEvent::class, static::class);
+ $dispatcher->addServiceListener(NodeRestoredEvent::class, static::class);
+ }
+
+ public function handle(Event $event): void {
+ if (!$this->encryptionManager->isEnabled()) {
+ return;
+ }
+ if ($event instanceof NodeRenamedEvent) {
+ $this->getUpdate()->postRename($event->getSource(), $event->getTarget());
+ } elseif ($event instanceof ShareCreatedEvent) {
+ $this->getUpdate()->postShared($event->getShare()->getNode());
+ } elseif ($event instanceof ShareDeletedEvent) {
+ // In case the unsharing happens in a background job, we don't have
+ // a session and we load instead the user from the UserManager
+ $owner = $event->getShare()->getNode()->getOwner();
+ $this->getUpdate($owner)->postUnshared($event->getShare()->getNode());
+ } elseif ($event instanceof NodeRestoredEvent) {
+ $this->getUpdate()->postRestore($event->getTarget());
+ }
+ }
+
+ private function getUpdate(?IUser $owner = null): Update {
+ if (is_null($this->updater)) {
+ $user = $this->userSession->getUser();
+ if (!$user && ($owner !== null)) {
+ $user = $owner;
+ }
+ if (!$user) {
+ throw new \Exception('Inconsistent data, File unshared, but owner not found. Should not happen');
+ }
+
+ $uid = $user->getUID();
+
+ if (!$this->setupManager->isSetupComplete($user)) {
+ $this->setupManager->setupForUser($user);
+ }
+
+ $this->updater = new Update(
+ new Util(
+ new View(),
+ \OC::$server->getUserManager(),
+ \OC::$server->getGroupManager(),
+ \OC::$server->getConfig()),
+ \OC::$server->getEncryptionManager(),
+ \OC::$server->get(IFile::class),
+ \OC::$server->get(LoggerInterface::class),
+ $uid
+ );
+ }
+
+ return $this->updater;
+ }
+}
diff --git a/lib/private/Encryption/EncryptionWrapper.php b/lib/private/Encryption/EncryptionWrapper.php
index 7f355b603d6..b9db9616538 100644
--- a/lib/private/Encryption/EncryptionWrapper.php
+++ b/lib/private/Encryption/EncryptionWrapper.php
@@ -75,15 +75,6 @@ class EncryptionWrapper {
\OC::$server->getGroupManager(),
\OC::$server->getConfig()
);
- $update = new Update(
- new View(),
- $util,
- Filesystem::getMountManager(),
- $this->manager,
- $fileHelper,
- $this->logger,
- $uid
- );
return new Encryption(
$parameters,
$this->manager,
@@ -92,7 +83,6 @@ class EncryptionWrapper {
$fileHelper,
$uid,
$keyStorage,
- $update,
$mountManager,
$this->arrayCache
);
diff --git a/lib/private/Encryption/HookManager.php b/lib/private/Encryption/HookManager.php
deleted file mode 100644
index 39e7edabb95..00000000000
--- a/lib/private/Encryption/HookManager.php
+++ /dev/null
@@ -1,75 +0,0 @@
-<?php
-
-/**
- * SPDX-FileCopyrightText: 2016-2024 Nextcloud GmbH and Nextcloud contributors
- * SPDX-FileCopyrightText: 2016 ownCloud, Inc.
- * SPDX-License-Identifier: AGPL-3.0-only
- */
-namespace OC\Encryption;
-
-use OC\Files\Filesystem;
-use OC\Files\SetupManager;
-use OC\Files\View;
-use OCP\Encryption\IFile;
-use Psr\Log\LoggerInterface;
-
-class HookManager {
- private static ?Update $updater = null;
-
- public static function postShared($params): void {
- self::getUpdate()->postShared($params);
- }
- public static function postUnshared($params): void {
- // In case the unsharing happens in a background job, we don't have
- // a session and we load instead the user from the UserManager
- $path = Filesystem::getPath($params['fileSource']);
- $owner = Filesystem::getOwner($path);
- self::getUpdate($owner)->postUnshared($params);
- }
-
- public static function postRename($params): void {
- self::getUpdate()->postRename($params);
- }
-
- public static function postRestore($params): void {
- self::getUpdate()->postRestore($params);
- }
-
- private static function getUpdate(?string $owner = null): Update {
- if (is_null(self::$updater)) {
- $user = \OC::$server->getUserSession()->getUser();
- if (!$user && $owner) {
- $user = \OC::$server->getUserManager()->get($owner);
- }
- if (!$user) {
- throw new \Exception('Inconsistent data, File unshared, but owner not found. Should not happen');
- }
-
- $uid = '';
- if ($user) {
- $uid = $user->getUID();
- }
-
- $setupManager = \OC::$server->get(SetupManager::class);
- if (!$setupManager->isSetupComplete($user)) {
- $setupManager->setupForUser($user);
- }
-
- self::$updater = new Update(
- new View(),
- new Util(
- new View(),
- \OC::$server->getUserManager(),
- \OC::$server->getGroupManager(),
- \OC::$server->getConfig()),
- Filesystem::getMountManager(),
- \OC::$server->getEncryptionManager(),
- \OC::$server->get(IFile::class),
- \OC::$server->get(LoggerInterface::class),
- $uid
- );
- }
-
- return self::$updater;
- }
-}
diff --git a/lib/private/Encryption/Update.php b/lib/private/Encryption/Update.php
index 0b27d63c19a..293a1ce653c 100644
--- a/lib/private/Encryption/Update.php
+++ b/lib/private/Encryption/Update.php
@@ -1,146 +1,85 @@
<?php
+declare(strict_types=1);
+
/**
* SPDX-FileCopyrightText: 2016-2024 Nextcloud GmbH and Nextcloud contributors
* SPDX-FileCopyrightText: 2016 ownCloud, Inc.
* SPDX-License-Identifier: AGPL-3.0-only
*/
+
namespace OC\Encryption;
use InvalidArgumentException;
-use OC\Files\Filesystem;
-use OC\Files\Mount;
use OC\Files\View;
use OCP\Encryption\Exceptions\GenericEncryptionException;
+use OCP\Files\File as OCPFile;
+use OCP\Files\Folder;
+use OCP\Files\NotFoundException;
use Psr\Log\LoggerInterface;
/**
* update encrypted files, e.g. because a file was shared
*/
class Update {
- /** @var View */
- protected $view;
-
- /** @var Util */
- protected $util;
-
- /** @var \OC\Files\Mount\Manager */
- protected $mountManager;
-
- /** @var Manager */
- protected $encryptionManager;
-
- /** @var string */
- protected $uid;
-
- /** @var File */
- protected $file;
-
- /** @var LoggerInterface */
- protected $logger;
-
- /**
- * @param string $uid
- */
public function __construct(
- View $view,
- Util $util,
- Mount\Manager $mountManager,
- Manager $encryptionManager,
- File $file,
- LoggerInterface $logger,
- $uid,
+ protected Util $util,
+ protected Manager $encryptionManager,
+ protected File $file,
+ protected LoggerInterface $logger,
+ protected string $uid,
) {
- $this->view = $view;
- $this->util = $util;
- $this->mountManager = $mountManager;
- $this->encryptionManager = $encryptionManager;
- $this->file = $file;
- $this->logger = $logger;
- $this->uid = $uid;
}
/**
* hook after file was shared
- *
- * @param array $params
*/
- public function postShared($params) {
- if ($this->encryptionManager->isEnabled()) {
- if ($params['itemType'] === 'file' || $params['itemType'] === 'folder') {
- $path = Filesystem::getPath($params['fileSource']);
- [$owner, $ownerPath] = $this->getOwnerPath($path);
- $absPath = '/' . $owner . '/files/' . $ownerPath;
- $this->update($absPath);
- }
- }
+ public function postShared(OCPFile|Folder $node): void {
+ $this->update($node);
}
/**
* hook after file was unshared
- *
- * @param array $params
*/
- public function postUnshared($params) {
- if ($this->encryptionManager->isEnabled()) {
- if ($params['itemType'] === 'file' || $params['itemType'] === 'folder') {
- $path = Filesystem::getPath($params['fileSource']);
- [$owner, $ownerPath] = $this->getOwnerPath($path);
- $absPath = '/' . $owner . '/files/' . $ownerPath;
- $this->update($absPath);
- }
- }
+ public function postUnshared(OCPFile|Folder $node): void {
+ $this->update($node);
}
/**
* inform encryption module that a file was restored from the trash bin,
* e.g. to update the encryption keys
- *
- * @param array $params
*/
- public function postRestore($params) {
- if ($this->encryptionManager->isEnabled()) {
- $path = Filesystem::normalizePath('/' . $this->uid . '/files/' . $params['filePath']);
- $this->update($path);
- }
+ public function postRestore(OCPFile|Folder $node): void {
+ $this->update($node);
}
/**
* inform encryption module that a file was renamed,
* e.g. to update the encryption keys
- *
- * @param array $params
*/
- public function postRename($params) {
- $source = $params['oldpath'];
- $target = $params['newpath'];
- if (
- $this->encryptionManager->isEnabled() &&
- dirname($source) !== dirname($target)
- ) {
- [$owner, $ownerPath] = $this->getOwnerPath($target);
- $absPath = '/' . $owner . '/files/' . $ownerPath;
- $this->update($absPath);
+ public function postRename(OCPFile|Folder $source, OCPFile|Folder $target): void {
+ if (dirname($source->getPath()) !== dirname($target->getPath())) {
+ $this->update($target);
}
}
/**
- * get owner and path relative to data/<owner>/files
+ * get owner and path relative to data/
*
- * @param string $path path to file for current user
- * @return array ['owner' => $owner, 'path' => $path]
* @throws \InvalidArgumentException
*/
- protected function getOwnerPath($path) {
- $info = Filesystem::getFileInfo($path);
- $owner = Filesystem::getOwner($path);
+ protected function getOwnerPath(OCPFile|Folder $node): string {
+ $owner = $node->getOwner()?->getUID();
+ if ($owner === null) {
+ throw new InvalidArgumentException('No owner found for ' . $node->getId());
+ }
$view = new View('/' . $owner . '/files');
- $path = $view->getPath($info->getId());
- if ($path === null) {
- throw new InvalidArgumentException('No file found for ' . $info->getId());
+ try {
+ $path = $view->getPath($node->getId());
+ } catch (NotFoundException $e) {
+ throw new InvalidArgumentException('No file found for ' . $node->getId(), previous:$e);
}
-
- return [$owner, $path];
+ return '/' . $owner . '/files/' . $path;
}
/**
@@ -149,7 +88,7 @@ class Update {
* @param string $path relative to data/
* @throws Exceptions\ModuleDoesNotExistsException
*/
- public function update($path) {
+ public function update(OCPFile|Folder $node): void {
$encryptionModule = $this->encryptionManager->getEncryptionModule();
// if the encryption module doesn't encrypt the files on a per-user basis
@@ -158,15 +97,14 @@ class Update {
return;
}
+ $path = $this->getOwnerPath($node);
// if a folder was shared, get a list of all (sub-)folders
- if ($this->view->is_dir($path)) {
+ if ($node instanceof Folder) {
$allFiles = $this->util->getAllFiles($path);
} else {
$allFiles = [$path];
}
-
-
foreach ($allFiles as $file) {
$usersSharing = $this->file->getAccessList($file);
try {
diff --git a/lib/private/Encryption/Util.php b/lib/private/Encryption/Util.php
index 1fb08b15696..0566ab9a760 100644
--- a/lib/private/Encryption/Util.php
+++ b/lib/private/Encryption/Util.php
@@ -304,7 +304,7 @@ class Util {
// detect user specific folders
if ($this->userManager->userExists($root[1])
- && in_array($root[2], $this->excludedPaths)) {
+ && in_array($root[2] ?? '', $this->excludedPaths)) {
return true;
}
}
diff --git a/lib/private/Files/Cache/Wrapper/CacheJail.php b/lib/private/Files/Cache/Wrapper/CacheJail.php
index 5c7bd4334f3..5bc4ee8529d 100644
--- a/lib/private/Files/Cache/Wrapper/CacheJail.php
+++ b/lib/private/Files/Cache/Wrapper/CacheJail.php
@@ -31,10 +31,13 @@ class CacheJail extends CacheWrapper {
) {
parent::__construct($cache, $dependencies);
- if ($cache instanceof CacheJail) {
- $this->unjailedRoot = $cache->getSourcePath($root);
- } else {
- $this->unjailedRoot = $root;
+ $this->unjailedRoot = $root;
+ $parent = $cache;
+ while ($parent instanceof CacheWrapper) {
+ if ($parent instanceof CacheJail) {
+ $this->unjailedRoot = $parent->getSourcePath($this->unjailedRoot);
+ }
+ $parent = $parent->getCache();
}
}
@@ -50,7 +53,7 @@ class CacheJail extends CacheWrapper {
*
* @return string
*/
- protected function getGetUnjailedRoot() {
+ public function getGetUnjailedRoot() {
return $this->unjailedRoot;
}
diff --git a/lib/private/Files/SimpleFS/SimpleFile.php b/lib/private/Files/SimpleFS/SimpleFile.php
index cbb3af4db29..0bfaea21788 100644
--- a/lib/private/Files/SimpleFS/SimpleFile.php
+++ b/lib/private/Files/SimpleFS/SimpleFile.php
@@ -6,9 +6,11 @@
namespace OC\Files\SimpleFS;
use OCP\Files\File;
+use OCP\Files\GenericFileException;
use OCP\Files\NotFoundException;
use OCP\Files\NotPermittedException;
use OCP\Files\SimpleFS\ISimpleFile;
+use OCP\Lock\LockedException;
class SimpleFile implements ISimpleFile {
private File $file;
@@ -48,8 +50,10 @@ class SimpleFile implements ISimpleFile {
/**
* Get the content
*
- * @throws NotPermittedException
+ * @throws GenericFileException
+ * @throws LockedException
* @throws NotFoundException
+ * @throws NotPermittedException
*/
public function getContent(): string {
$result = $this->file->getContent();
@@ -65,8 +69,10 @@ class SimpleFile implements ISimpleFile {
* Overwrite the file
*
* @param string|resource $data
- * @throws NotPermittedException
+ * @throws GenericFileException
+ * @throws LockedException
* @throws NotFoundException
+ * @throws NotPermittedException
*/
public function putContent($data): void {
try {
diff --git a/lib/private/Files/Storage/Temporary.php b/lib/private/Files/Storage/Temporary.php
index ff7a816930d..ecf8a1315a9 100644
--- a/lib/private/Files/Storage/Temporary.php
+++ b/lib/private/Files/Storage/Temporary.php
@@ -7,16 +7,20 @@
*/
namespace OC\Files\Storage;
+use OCP\Files;
+use OCP\ITempManager;
+use OCP\Server;
+
/**
* local storage backend in temporary folder for testing purpose
*/
class Temporary extends Local {
public function __construct(array $parameters = []) {
- parent::__construct(['datadir' => \OC::$server->getTempManager()->getTemporaryFolder()]);
+ parent::__construct(['datadir' => Server::get(ITempManager::class)->getTemporaryFolder()]);
}
public function cleanUp(): void {
- \OC_Helper::rmdirr($this->datadir);
+ Files::rmdirr($this->datadir);
}
public function __destruct() {
diff --git a/lib/private/Files/Storage/Wrapper/Encryption.php b/lib/private/Files/Storage/Wrapper/Encryption.php
index bdaba57687a..f4ab4754cff 100644
--- a/lib/private/Files/Storage/Wrapper/Encryption.php
+++ b/lib/private/Files/Storage/Wrapper/Encryption.php
@@ -8,7 +8,6 @@
namespace OC\Files\Storage\Wrapper;
use OC\Encryption\Exceptions\ModuleDoesNotExistsException;
-use OC\Encryption\Update;
use OC\Encryption\Util;
use OC\Files\Cache\CacheEntry;
use OC\Files\Filesystem;
@@ -50,7 +49,6 @@ class Encryption extends Wrapper {
private IFile $fileHelper,
private ?string $uid,
private IStorage $keyStorage,
- private Update $update,
private Manager $mountManager,
private ArrayCache $arrayCache,
) {
@@ -65,7 +63,8 @@ class Encryption extends Wrapper {
$info = $this->getCache()->get($path);
if ($info === false) {
- return false;
+ /* Pass call to wrapped storage, it may be a special file like a part file */
+ return $this->storage->filesize($path);
}
if (isset($this->unencryptedSize[$fullPath])) {
$size = $this->unencryptedSize[$fullPath];
@@ -319,7 +318,7 @@ class Encryption extends Wrapper {
if (!empty($encryptionModuleId)) {
$encryptionModule = $this->encryptionManager->getEncryptionModule($encryptionModuleId);
$shouldEncrypt = true;
- } elseif (empty($encryptionModuleId) && $info['encrypted'] === true) {
+ } elseif ($info !== false && $info['encrypted'] === true) {
// we come from a old installation. No header and/or no module defined
// but the file is encrypted. In this case we need to use the
// OC_DEFAULT_MODULE to read the file
@@ -537,10 +536,22 @@ class Encryption extends Wrapper {
$result = $this->copyBetweenStorage($sourceStorage, $sourceInternalPath, $targetInternalPath, $preserveMtime, true);
if ($result) {
- if ($sourceStorage->is_dir($sourceInternalPath)) {
- $result = $sourceStorage->rmdir($sourceInternalPath);
- } else {
- $result = $sourceStorage->unlink($sourceInternalPath);
+ $setPreserveCacheOnDelete = $sourceStorage->instanceOfStorage(ObjectStoreStorage::class) && !$this->instanceOfStorage(ObjectStoreStorage::class);
+ if ($setPreserveCacheOnDelete) {
+ /** @var ObjectStoreStorage $sourceStorage */
+ $sourceStorage->setPreserveCacheOnDelete(true);
+ }
+ try {
+ if ($sourceStorage->is_dir($sourceInternalPath)) {
+ $result = $sourceStorage->rmdir($sourceInternalPath);
+ } else {
+ $result = $sourceStorage->unlink($sourceInternalPath);
+ }
+ } finally {
+ if ($setPreserveCacheOnDelete) {
+ /** @var ObjectStoreStorage $sourceStorage */
+ $sourceStorage->setPreserveCacheOnDelete(false);
+ }
}
}
return $result;
@@ -665,7 +676,7 @@ class Encryption extends Wrapper {
if (is_resource($dh)) {
while ($result && ($file = readdir($dh)) !== false) {
if (!Filesystem::isIgnoredDir($file)) {
- $result &= $this->copyFromStorage($sourceStorage, $sourceInternalPath . '/' . $file, $targetInternalPath . '/' . $file, false, $isRename);
+ $result = $this->copyFromStorage($sourceStorage, $sourceInternalPath . '/' . $file, $targetInternalPath . '/' . $file, $preserveMtime, $isRename);
}
}
}
diff --git a/lib/private/Files/Type/Detection.php b/lib/private/Files/Type/Detection.php
index 42315247dbf..aeaac030413 100644
--- a/lib/private/Files/Type/Detection.php
+++ b/lib/private/Files/Type/Detection.php
@@ -9,6 +9,7 @@ declare(strict_types=1);
namespace OC\Files\Type;
use OCP\Files\IMimeTypeDetector;
+use OCP\IBinaryFinder;
use OCP\ITempManager;
use OCP\IURLGenerator;
use Psr\Log\LoggerInterface;
@@ -225,11 +226,13 @@ class Detection implements IMimeTypeDetector {
}
}
- if (\OC_Helper::canExecute('file')) {
+ $binaryFinder = \OCP\Server::get(IBinaryFinder::class);
+ $program = $binaryFinder->findBinaryPath('file');
+ if ($program !== false) {
// it looks like we have a 'file' command,
// lets see if it does have mime support
$path = escapeshellarg($path);
- $fp = popen("test -f $path && file -b --mime-type $path", 'r');
+ $fp = popen("test -f $path && $program -b --mime-type $path", 'r');
if ($fp !== false) {
$mimeType = fgets($fp);
pclose($fp);
diff --git a/lib/private/Installer.php b/lib/private/Installer.php
index 00fdd84c1bc..a1d27c9255b 100644
--- a/lib/private/Installer.php
+++ b/lib/private/Installer.php
@@ -19,6 +19,7 @@ use OC\DB\MigrationService;
use OC_App;
use OC_Helper;
use OCP\App\IAppManager;
+use OCP\Files;
use OCP\HintException;
use OCP\Http\Client\IClientService;
use OCP\IConfig;
@@ -324,14 +325,14 @@ class Installer {
$baseDir = OC_App::getInstallPath() . '/' . $appId;
// Remove old app with the ID if existent
- OC_Helper::rmdirr($baseDir);
+ Files::rmdirr($baseDir);
// Move to app folder
if (@mkdir($baseDir)) {
$extractDir .= '/' . $folders[0];
OC_Helper::copyr($extractDir, $baseDir);
}
OC_Helper::copyr($extractDir, $baseDir);
- OC_Helper::rmdirr($extractDir);
+ Files::rmdirr($extractDir);
return;
}
// Signature does not match
@@ -450,7 +451,7 @@ class Installer {
return false;
}
$appDir = OC_App::getInstallPath() . '/' . $appId;
- OC_Helper::rmdirr($appDir);
+ Files::rmdirr($appDir);
return true;
} else {
$this->logger->error('can\'t remove app ' . $appId . '. It is not installed.');
diff --git a/lib/private/Log/LogDetails.php b/lib/private/Log/LogDetails.php
index b3ae23a3770..8c1efaea20d 100644
--- a/lib/private/Log/LogDetails.php
+++ b/lib/private/Log/LogDetails.php
@@ -59,6 +59,10 @@ abstract class LogDetails {
'userAgent',
'version'
);
+ $clientReqId = $request->getHeader('X-Request-Id');
+ if ($clientReqId !== '') {
+ $entry['clientReqId'] = $clientReqId;
+ }
if (is_array($message)) {
// Exception messages are extracted and the exception is put into a separate field
diff --git a/lib/private/Repair/MoveUpdaterStepFile.php b/lib/private/Repair/MoveUpdaterStepFile.php
index c9b51b308c4..eb9f78b0a39 100644
--- a/lib/private/Repair/MoveUpdaterStepFile.php
+++ b/lib/private/Repair/MoveUpdaterStepFile.php
@@ -5,6 +5,7 @@
*/
namespace OC\Repair;
+use OCP\Files;
use OCP\Migration\IOutput;
use OCP\Migration\IRepairStep;
@@ -40,7 +41,7 @@ class MoveUpdaterStepFile implements IRepairStep {
// cleanup
if (file_exists($previousStepFile)) {
- if (\OC_Helper::rmdirr($previousStepFile)) {
+ if (Files::rmdirr($previousStepFile)) {
$output->info('.step-previous-update removed');
} else {
$output->info('.step-previous-update can\'t be removed - abort move of .step file');
diff --git a/lib/private/Route/Router.php b/lib/private/Route/Router.php
index d073132516d..2a60287254b 100644
--- a/lib/private/Route/Router.php
+++ b/lib/private/Route/Router.php
@@ -54,9 +54,9 @@ class Router implements IRouter {
protected LoggerInterface $logger,
IRequest $request,
private IConfig $config,
- private IEventLogger $eventLogger,
+ protected IEventLogger $eventLogger,
private ContainerInterface $container,
- private IAppManager $appManager,
+ protected IAppManager $appManager,
) {
$baseUrl = \OC::$WEBROOT;
if (!($config->getSystemValue('htaccess.IgnoreFrontController', false) === true || getenv('front_controller_active') === 'true')) {
@@ -116,9 +116,11 @@ class Router implements IRouter {
$this->loaded = true;
$routingFiles = $this->getRoutingFiles();
+ $this->eventLogger->start('route:load:attributes', 'Loading Routes from attributes');
foreach (\OC_App::getEnabledApps() as $enabledApp) {
$this->loadAttributeRoutes($enabledApp);
}
+ $this->eventLogger->end('route:load:attributes');
} else {
if (isset($this->loadedApps[$app])) {
return;
@@ -140,6 +142,7 @@ class Router implements IRouter {
}
}
+ $this->eventLogger->start('route:load:files', 'Loading Routes from files');
foreach ($routingFiles as $app => $file) {
if (!isset($this->loadedApps[$app])) {
if (!$this->appManager->isAppLoaded($app)) {
@@ -160,6 +163,7 @@ class Router implements IRouter {
$this->root->addCollection($collection);
}
}
+ $this->eventLogger->end('route:load:files');
if (!isset($this->loadedApps['core'])) {
$this->loadedApps['core'] = true;
@@ -265,6 +269,7 @@ class Router implements IRouter {
$this->loadRoutes();
}
+ $this->eventLogger->start('route:url:match', 'Symfony url matcher call');
$matcher = new UrlMatcher($this->root, $this->context);
try {
$parameters = $matcher->match($url);
@@ -283,6 +288,7 @@ class Router implements IRouter {
throw $e;
}
}
+ $this->eventLogger->end('route:url:match');
$this->eventLogger->end('route:match');
return $parameters;
diff --git a/lib/private/Security/RateLimiting/Limiter.php b/lib/private/Security/RateLimiting/Limiter.php
index b7ac26d9132..316becfa009 100644
--- a/lib/private/Security/RateLimiting/Limiter.php
+++ b/lib/private/Security/RateLimiting/Limiter.php
@@ -13,10 +13,12 @@ use OC\Security\RateLimiting\Backend\IBackend;
use OC\Security\RateLimiting\Exception\RateLimitExceededException;
use OCP\IUser;
use OCP\Security\RateLimiting\ILimiter;
+use Psr\Log\LoggerInterface;
class Limiter implements ILimiter {
public function __construct(
private IBackend $backend,
+ private LoggerInterface $logger,
) {
}
@@ -32,6 +34,11 @@ class Limiter implements ILimiter {
): void {
$existingAttempts = $this->backend->getAttempts($methodIdentifier, $userIdentifier);
if ($existingAttempts >= $limit) {
+ $this->logger->info('Request blocked because it exceeds the rate limit [method: {method}, limit: {limit}, period: {period}]', [
+ 'method' => $methodIdentifier,
+ 'limit' => $limit,
+ 'period' => $period,
+ ]);
throw new RateLimitExceededException();
}
diff --git a/lib/private/ServerContainer.php b/lib/private/ServerContainer.php
index 9f887b2d48a..b5bcbdaeb6f 100644
--- a/lib/private/ServerContainer.php
+++ b/lib/private/ServerContainer.php
@@ -128,18 +128,17 @@ class ServerContainer extends SimpleContainer {
} catch (QueryException $e) {
// Continue with general autoloading then
}
- }
-
- // In case the service starts with OCA\ we try to find the service in
- // the apps container first.
- if (($appContainer = $this->getAppContainerForService($name)) !== null) {
- try {
- return $appContainer->queryNoFallback($name);
- } catch (QueryException $e) {
- // Didn't find the service or the respective app container
- // In this case the service won't be part of the core container,
- // so we can throw directly
- throw $e;
+ // In case the service starts with OCA\ we try to find the service in
+ // the apps container first.
+ if (($appContainer = $this->getAppContainerForService($name)) !== null) {
+ try {
+ return $appContainer->queryNoFallback($name);
+ } catch (QueryException $e) {
+ // Didn't find the service or the respective app container
+ // In this case the service won't be part of the core container,
+ // so we can throw directly
+ throw $e;
+ }
}
} elseif (str_starts_with($name, 'OC\\Settings\\') && substr_count($name, '\\') >= 3) {
$segments = explode('\\', $name);
diff --git a/lib/private/TempManager.php b/lib/private/TempManager.php
index b7dccad3f95..4c0ffcf43d7 100644
--- a/lib/private/TempManager.php
+++ b/lib/private/TempManager.php
@@ -8,6 +8,7 @@
namespace OC;
use bantu\IniGetWrapper\IniGetWrapper;
+use OCP\Files;
use OCP\IConfig;
use OCP\ITempManager;
use OCP\Security\ISecureRandom;
@@ -99,7 +100,7 @@ class TempManager implements ITempManager {
foreach ($files as $file) {
if (file_exists($file)) {
try {
- \OC_Helper::rmdirr($file);
+ Files::rmdirr($file);
} catch (\UnexpectedValueException $ex) {
$this->log->warning(
'Error deleting temporary file/folder: {file} - Reason: {error}',
diff --git a/lib/private/User/User.php b/lib/private/User/User.php
index f04977314e2..8e01a15695c 100644
--- a/lib/private/User/User.php
+++ b/lib/private/User/User.php
@@ -11,7 +11,6 @@ use InvalidArgumentException;
use OC\Accounts\AccountManager;
use OC\Avatar\AvatarManager;
use OC\Hooks\Emitter;
-use OC_Helper;
use OCP\Accounts\IAccountManager;
use OCP\Comments\ICommentsManager;
use OCP\EventDispatcher\IEventDispatcher;
@@ -570,11 +569,11 @@ class User implements IUser {
public function setQuota($quota) {
$oldQuota = $this->config->getUserValue($this->uid, 'files', 'quota', '');
if ($quota !== 'none' and $quota !== 'default') {
- $bytesQuota = OC_Helper::computerFileSize($quota);
+ $bytesQuota = \OCP\Util::computerFileSize($quota);
if ($bytesQuota === false) {
throw new InvalidArgumentException('Failed to set quota to invalid value ' . $quota);
}
- $quota = OC_Helper::humanFileSize($bytesQuota);
+ $quota = \OCP\Util::humanFileSize($bytesQuota);
}
if ($quota !== $oldQuota) {
$this->config->setUserValue($this->uid, 'files', 'quota', $quota);
diff --git a/lib/private/legacy/OC_Helper.php b/lib/private/legacy/OC_Helper.php
index a89cbe1bb3a..172c865364c 100644
--- a/lib/private/legacy/OC_Helper.php
+++ b/lib/private/legacy/OC_Helper.php
@@ -39,75 +39,26 @@ class OC_Helper {
* Make a human file size
* @param int|float $bytes file size in bytes
* @return string a human readable file size
+ * @deprecated 4.0.0 replaced with \OCP\Util::humanFileSize
*
* Makes 2048 to 2 kB.
*/
public static function humanFileSize(int|float $bytes): string {
- if ($bytes < 0) {
- return '?';
- }
- if ($bytes < 1024) {
- return "$bytes B";
- }
- $bytes = round($bytes / 1024, 0);
- if ($bytes < 1024) {
- return "$bytes KB";
- }
- $bytes = round($bytes / 1024, 1);
- if ($bytes < 1024) {
- return "$bytes MB";
- }
- $bytes = round($bytes / 1024, 1);
- if ($bytes < 1024) {
- return "$bytes GB";
- }
- $bytes = round($bytes / 1024, 1);
- if ($bytes < 1024) {
- return "$bytes TB";
- }
-
- $bytes = round($bytes / 1024, 1);
- return "$bytes PB";
+ return \OCP\Util::humanFileSize($bytes);
}
/**
* Make a computer file size
* @param string $str file size in human readable format
* @return false|int|float a file size in bytes
+ * @deprecated 4.0.0 Use \OCP\Util::computerFileSize
*
* Makes 2kB to 2048.
*
* Inspired by: https://www.php.net/manual/en/function.filesize.php#92418
*/
public static function computerFileSize(string $str): false|int|float {
- $str = strtolower($str);
- if (is_numeric($str)) {
- return Util::numericToNumber($str);
- }
-
- $bytes_array = [
- 'b' => 1,
- 'k' => 1024,
- 'kb' => 1024,
- 'mb' => 1024 * 1024,
- 'm' => 1024 * 1024,
- 'gb' => 1024 * 1024 * 1024,
- 'g' => 1024 * 1024 * 1024,
- 'tb' => 1024 * 1024 * 1024 * 1024,
- 't' => 1024 * 1024 * 1024 * 1024,
- 'pb' => 1024 * 1024 * 1024 * 1024 * 1024,
- 'p' => 1024 * 1024 * 1024 * 1024 * 1024,
- ];
-
- $bytes = (float)$str;
-
- if (preg_match('#([kmgtp]?b?)$#si', $str, $matches) && isset($bytes_array[$matches[1]])) {
- $bytes *= $bytes_array[$matches[1]];
- } else {
- return false;
- }
-
- return Util::numericToNumber(round($bytes));
+ return \OCP\Util::computerFileSize($str);
}
/**
@@ -144,37 +95,10 @@ class OC_Helper {
* @param string $dir path to the folder
* @param bool $deleteSelf if set to false only the content of the folder will be deleted
* @return bool
+ * @deprecated 5.0.0 use \OCP\Files::rmdirr instead
*/
public static function rmdirr($dir, $deleteSelf = true) {
- if (is_dir($dir)) {
- $files = new RecursiveIteratorIterator(
- new RecursiveDirectoryIterator($dir, RecursiveDirectoryIterator::SKIP_DOTS),
- RecursiveIteratorIterator::CHILD_FIRST
- );
-
- foreach ($files as $fileInfo) {
- /** @var SplFileInfo $fileInfo */
- if ($fileInfo->isLink()) {
- unlink($fileInfo->getPathname());
- } elseif ($fileInfo->isDir()) {
- rmdir($fileInfo->getRealPath());
- } else {
- unlink($fileInfo->getRealPath());
- }
- }
- if ($deleteSelf) {
- rmdir($dir);
- }
- } elseif (file_exists($dir)) {
- if ($deleteSelf) {
- unlink($dir);
- }
- }
- if (!$deleteSelf) {
- return true;
- }
-
- return !file_exists($dir);
+ return \OCP\Files::rmdirr($dir, $deleteSelf);
}
/**
@@ -196,6 +120,7 @@ class OC_Helper {
* @internal param string $program name
* @internal param string $optional search path, defaults to $PATH
* @return bool true if executable program found in path
+ * @deprecated 32.0.0 use the \OCP\IBinaryFinder
*/
public static function canExecute($name, $path = false) {
// path defaults to PATH from environment if not set
diff --git a/lib/private/legacy/OC_Util.php b/lib/private/legacy/OC_Util.php
index 580fec7b5b3..895cfba35c5 100644
--- a/lib/private/legacy/OC_Util.php
+++ b/lib/private/legacy/OC_Util.php
@@ -107,7 +107,7 @@ class OC_Util {
if ($userQuota === 'none') {
return \OCP\Files\FileInfo::SPACE_UNLIMITED;
}
- return OC_Helper::computerFileSize($userQuota);
+ return \OCP\Util::computerFileSize($userQuota);
}
/**
diff --git a/lib/public/Accounts/IAccountManager.php b/lib/public/Accounts/IAccountManager.php
index a15651eb5e6..92fc0002674 100644
--- a/lib/public/Accounts/IAccountManager.php
+++ b/lib/public/Accounts/IAccountManager.php
@@ -48,30 +48,6 @@ interface IAccountManager {
public const SCOPE_PUBLISHED = 'v2-published';
/**
- * Contact details only visible locally
- *
- * @since 15.0.0
- * @deprecated 21.0.1
- */
- public const VISIBILITY_PRIVATE = 'private';
-
- /**
- * Contact details visible on trusted federated servers.
- *
- * @since 15.0.0
- * @deprecated 21.0.1
- */
- public const VISIBILITY_CONTACTS_ONLY = 'contacts';
-
- /**
- * Contact details visible on trusted federated servers and in the public lookup server.
- *
- * @since 15.0.0
- * @deprecated 21.0.1
- */
- public const VISIBILITY_PUBLIC = 'public';
-
- /**
* The list of allowed scopes
*
* @since 25.0.0
@@ -81,9 +57,6 @@ interface IAccountManager {
self::SCOPE_LOCAL,
self::SCOPE_FEDERATED,
self::SCOPE_PUBLISHED,
- self::VISIBILITY_PRIVATE,
- self::VISIBILITY_CONTACTS_ONLY,
- self::VISIBILITY_PUBLIC,
];
/**
@@ -98,6 +71,7 @@ interface IAccountManager {
/**
* @since 27.0.0
+ * @deprecated 27.0.0 only added for backwards compatibility with provisioning_api UsersController::getCurrentUser
*/
public const PROPERTY_DISPLAYNAME_LEGACY = 'display-name';
diff --git a/lib/public/Files.php b/lib/public/Files.php
index 62c41c4ada1..fb03a4192fc 100644
--- a/lib/public/Files.php
+++ b/lib/public/Files.php
@@ -18,12 +18,44 @@ namespace OCP;
class Files {
/**
* Recursive deletion of folders
+ *
+ * @param string $dir path to the folder
+ * @param bool $deleteSelf if set to false only the content of the folder will be deleted
* @return bool
* @since 5.0.0
+ * @since 32.0.0 added the $deleteSelf parameter
* @deprecated 14.0.0
*/
- public static function rmdirr($dir) {
- return \OC_Helper::rmdirr($dir);
+ public static function rmdirr($dir, bool $deleteSelf = true) {
+ if (is_dir($dir)) {
+ $files = new \RecursiveIteratorIterator(
+ new \RecursiveDirectoryIterator($dir, \RecursiveDirectoryIterator::SKIP_DOTS),
+ \RecursiveIteratorIterator::CHILD_FIRST
+ );
+
+ foreach ($files as $fileInfo) {
+ /** @var \SplFileInfo $fileInfo */
+ if ($fileInfo->isLink()) {
+ unlink($fileInfo->getPathname());
+ } elseif ($fileInfo->isDir()) {
+ rmdir($fileInfo->getRealPath());
+ } else {
+ unlink($fileInfo->getRealPath());
+ }
+ }
+ if ($deleteSelf) {
+ rmdir($dir);
+ }
+ } elseif (file_exists($dir)) {
+ if ($deleteSelf) {
+ unlink($dir);
+ }
+ }
+ if (!$deleteSelf) {
+ return true;
+ }
+
+ return !file_exists($dir);
}
/**
diff --git a/lib/public/Files/SimpleFS/ISimpleFile.php b/lib/public/Files/SimpleFS/ISimpleFile.php
index 2682c22580d..10cdc0a919d 100644
--- a/lib/public/Files/SimpleFS/ISimpleFile.php
+++ b/lib/public/Files/SimpleFS/ISimpleFile.php
@@ -5,8 +5,10 @@
*/
namespace OCP\Files\SimpleFS;
+use OCP\Files\GenericFileException;
use OCP\Files\NotFoundException;
use OCP\Files\NotPermittedException;
+use OCP\Lock\LockedException;
/**
* This interface allows to manage simple files.
@@ -49,8 +51,10 @@ interface ISimpleFile {
/**
* Get the content
*
- * @throws NotPermittedException
+ * @throws GenericFileException
+ * @throws LockedException
* @throws NotFoundException
+ * @throws NotPermittedException
* @since 11.0.0
*/
public function getContent(): string;
@@ -59,8 +63,10 @@ interface ISimpleFile {
* Overwrite the file
*
* @param string|resource $data
- * @throws NotPermittedException
+ * @throws GenericFileException
+ * @throws LockedException
* @throws NotFoundException
+ * @throws NotPermittedException
* @since 11.0.0
*/
public function putContent($data): void;
diff --git a/lib/public/Template.php b/lib/public/Template.php
index 3b31ee10a54..715115bc635 100644
--- a/lib/public/Template.php
+++ b/lib/public/Template.php
@@ -77,7 +77,7 @@ class Template extends \OC_Template implements ITemplate {
}
/**
- * Make OC_Helper::humanFileSize available as a simple function
+ * Make \OCP\Util::humanFileSize available as a simple function
* Example: 2048 to 2 kB.
*
* @param int $bytes in bytes
diff --git a/lib/public/Util.php b/lib/public/Util.php
index 14663abd62f..d7cfd65ba56 100644
--- a/lib/public/Util.php
+++ b/lib/public/Util.php
@@ -332,19 +332,70 @@ class Util {
* @since 4.0.0
*/
public static function humanFileSize(int|float $bytes): string {
- return \OC_Helper::humanFileSize($bytes);
+ if ($bytes < 0) {
+ return '?';
+ }
+ if ($bytes < 1024) {
+ return "$bytes B";
+ }
+ $bytes = round($bytes / 1024, 0);
+ if ($bytes < 1024) {
+ return "$bytes KB";
+ }
+ $bytes = round($bytes / 1024, 1);
+ if ($bytes < 1024) {
+ return "$bytes MB";
+ }
+ $bytes = round($bytes / 1024, 1);
+ if ($bytes < 1024) {
+ return "$bytes GB";
+ }
+ $bytes = round($bytes / 1024, 1);
+ if ($bytes < 1024) {
+ return "$bytes TB";
+ }
+
+ $bytes = round($bytes / 1024, 1);
+ return "$bytes PB";
}
/**
* Make a computer file size (2 kB to 2048)
+ * Inspired by: https://www.php.net/manual/en/function.filesize.php#92418
+ *
* @param string $str file size in a fancy format
* @return false|int|float a file size in bytes
- *
- * Inspired by: https://www.php.net/manual/en/function.filesize.php#92418
* @since 4.0.0
*/
public static function computerFileSize(string $str): false|int|float {
- return \OC_Helper::computerFileSize($str);
+ $str = strtolower($str);
+ if (is_numeric($str)) {
+ return Util::numericToNumber($str);
+ }
+
+ $bytes_array = [
+ 'b' => 1,
+ 'k' => 1024,
+ 'kb' => 1024,
+ 'mb' => 1024 * 1024,
+ 'm' => 1024 * 1024,
+ 'gb' => 1024 * 1024 * 1024,
+ 'g' => 1024 * 1024 * 1024,
+ 'tb' => 1024 * 1024 * 1024 * 1024,
+ 't' => 1024 * 1024 * 1024 * 1024,
+ 'pb' => 1024 * 1024 * 1024 * 1024 * 1024,
+ 'p' => 1024 * 1024 * 1024 * 1024 * 1024,
+ ];
+
+ $bytes = (float)$str;
+
+ if (preg_match('#([kmgtp]?b?)$#si', $str, $matches) && isset($bytes_array[$matches[1]])) {
+ $bytes *= $bytes_array[$matches[1]];
+ } else {
+ return false;
+ }
+
+ return Util::numericToNumber(round($bytes));
}
/**