Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/nextcloud/server.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorRobin Appelman <robin@icewind.nl>2022-03-28 19:45:06 +0300
committerRobin Appelman <robin@icewind.nl>2022-04-04 15:57:56 +0300
commit99ac46d8f5de241b49e33e2c4fb874270f6860cc (patch)
tree4275e6e959229c742ee369fc0a439e4312c15816 /lib
parent74c97e257132384be3d6e0978b847c9d6933928b (diff)
allow getting mounts by providers
Signed-off-by: Robin Appelman <robin@icewind.nl>
Diffstat (limited to 'lib')
-rw-r--r--lib/private/Files/Config/MountProviderCollection.php4
-rw-r--r--lib/private/Files/Mount/Manager.php18
-rw-r--r--lib/private/Files/SetupManager.php98
-rw-r--r--lib/public/Files/Config/IMountProviderCollection.php4
4 files changed, 100 insertions, 24 deletions
diff --git a/lib/private/Files/Config/MountProviderCollection.php b/lib/private/Files/Config/MountProviderCollection.php
index 2b0acf7d69d..334fce15d9e 100644
--- a/lib/private/Files/Config/MountProviderCollection.php
+++ b/lib/private/Files/Config/MountProviderCollection.php
@@ -97,10 +97,10 @@ class MountProviderCollection implements IMountProviderCollection, Emitter {
return $this->getUserMountsForProviders($user, $this->providers);
}
- public function getUserMountsForProviderClass(IUser $user, string $mountProviderClass): array {
+ public function getUserMountsForProviderClasses(IUser $user, array $mountProviderClasses): array {
$providers = array_filter(
$this->providers,
- fn (IMountProvider $mountProvider) => (get_class($mountProvider) === $mountProviderClass)
+ fn (IMountProvider $mountProvider) => (in_array(get_class($mountProvider), $mountProviderClasses))
);
return $this->getUserMountsForProviders($user, $providers);
}
diff --git a/lib/private/Files/Mount/Manager.php b/lib/private/Files/Mount/Manager.php
index ecd97760f17..d0f5f3f5a52 100644
--- a/lib/private/Files/Mount/Manager.php
+++ b/lib/private/Files/Mount/Manager.php
@@ -204,4 +204,22 @@ class Manager implements IMountManager {
public function getSetupManager(): SetupManager {
return $this->setupManager;
}
+
+ /**
+ * Return all mounts in a path from a specific mount provider
+ *
+ * @param string $path
+ * @param string[] $mountProviders
+ * @return MountPoint[]
+ */
+ public function getMountsByMountProvider(string $path, array $mountProviders) {
+ $this->getSetupManager()->setupForProvider($path, $mountProviders);
+ if (in_array('', $mountProviders)) {
+ return $this->mounts;
+ } else {
+ return array_filter($this->mounts, function ($mount) use ($mountProviders) {
+ return in_array($mount->getMountProvider(), $mountProviders);
+ });
+ }
+ }
}
diff --git a/lib/private/Files/SetupManager.php b/lib/private/Files/SetupManager.php
index da50983da32..ddb0bbceb81 100644
--- a/lib/private/Files/SetupManager.php
+++ b/lib/private/Files/SetupManager.php
@@ -40,6 +40,7 @@ use OC_Util;
use OCP\Constants;
use OCP\Diagnostics\IEventLogger;
use OCP\EventDispatcher\IEventDispatcher;
+use OCP\Files\Config\IHomeMountProvider;
use OCP\Files\Config\IMountProvider;
use OCP\Files\Config\IUserMountCache;
use OCP\Files\Events\InvalidateMountCacheEvent;
@@ -263,6 +264,11 @@ class SetupManager {
return strpos($mount->getMountPoint(), $userRoot) === 0;
});
$this->userMountCache->registerMounts($user, $mounts);
+
+ $cacheDuration = $this->config->getSystemValueInt('fs_mount_cache_duration', 5 * 60);
+ if ($cacheDuration > 0) {
+ $this->cache->set($user->getUID(), true, $cacheDuration);
+ }
}
/**
@@ -321,25 +327,32 @@ class SetupManager {
}
/**
- * Set up the filesystem for the specified path
+ * Get the user to setup for a path or `null` if the root needs to be setup
+ *
+ * @param string $path
+ * @return IUser|null
*/
- public function setupForPath(string $path, bool $includeChildren = false): void {
+ private function getUserForPath(string $path) {
if (substr_count($path, '/') < 2) {
if ($user = $this->userSession->getUser()) {
- $this->setupForUser($user);
+ return $user;
} else {
- $this->setupRoot();
+ return null;
}
- return;
} elseif (strpos($path, '/appdata_' . \OC_Util::getInstanceId()) === 0 || strpos($path, '/files_external/') === 0) {
- $this->setupRoot();
- return;
+ return null;
} else {
[, $userId] = explode('/', $path);
}
- $user = $this->userManager->get($userId);
+ return $this->userManager->get($userId);
+ }
+ /**
+ * Set up the filesystem for the specified path
+ */
+ public function setupForPath(string $path, bool $includeChildren = false): void {
+ $user = $this->getUserForPath($path);
if (!$user) {
$this->setupRoot();
return;
@@ -349,17 +362,8 @@ class SetupManager {
return;
}
- // we perform a "cached" setup only after having done the full setup recently
- // this is also used to trigger a full setup after handling events that are likely
- // to change the available mounts
- $cachedSetup = $this->cache->get($user->getUID());
- if (!$cachedSetup) {
+ if ($this->fullSetupRequired($user)) {
$this->setupForUser($user);
-
- $cacheDuration = $this->config->getSystemValueInt('fs_mount_cache_duration', 5 * 60);
- if ($cacheDuration > 0) {
- $this->cache->set($user->getUID(), true, $cacheDuration);
- }
return;
}
@@ -381,7 +385,7 @@ class SetupManager {
$setupProviders[] = $cachedMount->getMountProvider();
$currentProviders[] = $cachedMount->getMountProvider();
if ($cachedMount->getMountProvider()) {
- $mounts = $this->mountProviderCollection->getUserMountsForProviderClass($user, $cachedMount->getMountProvider());
+ $mounts = $this->mountProviderCollection->getUserMountsForProviderClasses($user, [$cachedMount->getMountProvider()]);
} else {
$this->logger->debug("mount at " . $cachedMount->getMountPoint() . " has no provider set, performing full setup");
$this->setupForUser($user);
@@ -396,7 +400,7 @@ class SetupManager {
$setupProviders[] = $cachedMount->getMountProvider();
$currentProviders[] = $cachedMount->getMountProvider();
if ($cachedMount->getMountProvider()) {
- $mounts = array_merge($mounts, $this->mountProviderCollection->getUserMountsForProviderClass($user, $cachedMount->getMountProvider()));
+ $mounts = array_merge($mounts, $this->mountProviderCollection->getUserMountsForProviderClasses($user, [$cachedMount->getMountProvider()]));
} else {
$this->logger->debug("mount at " . $cachedMount->getMountPoint() . " has no provider set, performing full setup");
$this->setupForUser($user);
@@ -416,6 +420,60 @@ class SetupManager {
}
}
+ private function fullSetupRequired(IUser $user): bool {
+ // we perform a "cached" setup only after having done the full setup recently
+ // this is also used to trigger a full setup after handling events that are likely
+ // to change the available mounts
+ return !$this->cache->get($user->getUID());
+ }
+
+ /**
+ * @param string $path
+ * @param string[] $providers
+ */
+ public function setupForProvider(string $path, array $providers): void {
+ $user = $this->getUserForPath($path);
+ if (!$user) {
+ $this->setupRoot();
+ return;
+ }
+
+ if ($this->isSetupComplete($user)) {
+ return;
+ }
+
+ if ($this->fullSetupRequired($user)) {
+ $this->setupForUser($user);
+ return;
+ }
+
+ // home providers are always used
+ $providers = array_filter($providers, function (string $provider) {
+ return !is_subclass_of($provider, IHomeMountProvider::class);
+ });
+
+ if (in_array('', $providers)) {
+ $this->setupForUser($user);
+ }
+ $setupProviders = $this->setupUserMountProviders[$user->getUID()] ?? [];
+
+ $providers = array_diff($providers, $setupProviders);
+ if (count($providers) === 0) {
+ if (!$this->isSetupStarted($user)) {
+ $this->oneTimeUserSetup($user);
+ }
+ return;
+ } else {
+ $this->setupUserMountProviders[$user->getUID()] = array_merge($setupProviders, $providers);
+ $mounts = $this->mountProviderCollection->getUserMountsForProviderClasses($user, $providers);
+ }
+
+ $this->userMountCache->registerMounts($user, $mounts, $providers);
+ $this->setupForUserWith($user, function () use ($mounts) {
+ array_walk($mounts, [$this->mountManager, 'addMount']);
+ });
+ }
+
public function tearDown() {
$this->setupUsers = [];
$this->setupUsersComplete = [];
diff --git a/lib/public/Files/Config/IMountProviderCollection.php b/lib/public/Files/Config/IMountProviderCollection.php
index 5894d06a388..2d42246b863 100644
--- a/lib/public/Files/Config/IMountProviderCollection.php
+++ b/lib/public/Files/Config/IMountProviderCollection.php
@@ -42,11 +42,11 @@ interface IMountProviderCollection {
* Get the configured mount points for the user from a specific mount provider
*
* @param \OCP\IUser $user
- * @param class-string<IMountProvider> $mountProviderClass
+ * @param class-string<IMountProvider>[] $mountProviderClasses
* @return \OCP\Files\Mount\IMountPoint[]
* @since 24.0.0
*/
- public function getUserMountsForProviderClass(IUser $user, string $mountProviderClass);
+ public function getUserMountsForProviderClasses(IUser $user, array $mountProviderClasses): array;
/**
* Get the configured home mount for this user