[Pkg-owncloud-commits] [owncloud] 90/215: propagate etags for all user of a share
David Prévot
taffit at moszumanska.debian.org
Tue May 5 01:01:27 UTC 2015
This is an automated email from the git hooks/post-receive script.
taffit pushed a commit to branch stable8
in repository owncloud.
commit 30ad56813a16908e3862c353256f2a6d0f05fe3a
Author: Robin Appelman <icewind at owncloud.com>
Date: Mon Mar 9 16:20:18 2015 +0100
propagate etags for all user of a share
---
apps/files_sharing/appinfo/app.php | 37 ++++---
apps/files_sharing/appinfo/application.php | 51 ++++++++++
apps/files_sharing/appinfo/routes.php | 3 -
apps/files_sharing/lib/helper.php | 2 -
apps/files_sharing/lib/mountprovider.php | 70 +++++++++++++
.../lib/propagation/changewatcher.php | 56 ++++++++++
.../lib/propagation/propagationmanager.php | 113 +++++++++++++++++++++
.../lib/propagation/recipientpropagator.php | 108 ++++++++++++++++++++
apps/files_sharing/lib/sharedmount.php | 18 ++++
apps/files_sharing/lib/sharedstorage.php | 50 ++++-----
apps/files_sharing/lib/updater.php | 39 -------
apps/files_sharing/tests/propagation.php | 48 +++++++++
apps/files_sharing/tests/testcase.php | 7 +-
lib/private/share/share.php | 12 +++
14 files changed, 521 insertions(+), 93 deletions(-)
diff --git a/apps/files_sharing/appinfo/app.php b/apps/files_sharing/appinfo/app.php
index d009fbc..19d3b6c 100644
--- a/apps/files_sharing/appinfo/app.php
+++ b/apps/files_sharing/appinfo/app.php
@@ -25,31 +25,38 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>
*
*/
+
+namespace OCA\Files_Sharing\Appinfo;
+
$l = \OC::$server->getL10N('files_sharing');
-OC::$CLASSPATH['OC_Share_Backend_File'] = 'files_sharing/lib/share/file.php';
-OC::$CLASSPATH['OC_Share_Backend_Folder'] = 'files_sharing/lib/share/folder.php';
-OC::$CLASSPATH['OC\Files\Storage\Shared'] = 'files_sharing/lib/sharedstorage.php';
-OC::$CLASSPATH['OC\Files\Cache\SharedScanner'] = 'files_sharing/lib/scanner.php';
-OC::$CLASSPATH['OC\Files\Cache\Shared_Cache'] = 'files_sharing/lib/cache.php';
-OC::$CLASSPATH['OC\Files\Cache\Shared_Permissions'] = 'files_sharing/lib/permissions.php';
-OC::$CLASSPATH['OC\Files\Cache\Shared_Updater'] = 'files_sharing/lib/updater.php';
-OC::$CLASSPATH['OC\Files\Cache\Shared_Watcher'] = 'files_sharing/lib/watcher.php';
-OC::$CLASSPATH['OCA\Files\Share\Maintainer'] = 'files_sharing/lib/maintainer.php';
-OC::$CLASSPATH['OCA\Files\Share\Proxy'] = 'files_sharing/lib/proxy.php';
+\OC::$CLASSPATH['OC_Share_Backend_File'] = 'files_sharing/lib/share/file.php';
+\OC::$CLASSPATH['OC_Share_Backend_Folder'] = 'files_sharing/lib/share/folder.php';
+\OC::$CLASSPATH['OC\Files\Storage\Shared'] = 'files_sharing/lib/sharedstorage.php';
+\OC::$CLASSPATH['OC\Files\Cache\SharedScanner'] = 'files_sharing/lib/scanner.php';
+\OC::$CLASSPATH['OC\Files\Cache\Shared_Cache'] = 'files_sharing/lib/cache.php';
+\OC::$CLASSPATH['OC\Files\Cache\Shared_Permissions'] = 'files_sharing/lib/permissions.php';
+\OC::$CLASSPATH['OC\Files\Cache\Shared_Updater'] = 'files_sharing/lib/updater.php';
+\OC::$CLASSPATH['OC\Files\Cache\Shared_Watcher'] = 'files_sharing/lib/watcher.php';
+\OC::$CLASSPATH['OCA\Files\Share\Maintainer'] = 'files_sharing/lib/maintainer.php';
+\OC::$CLASSPATH['OCA\Files\Share\Proxy'] = 'files_sharing/lib/proxy.php';
// Exceptions
-OC::$CLASSPATH['OCA\Files_Sharing\Exceptions\BrokenPath'] = 'files_sharing/lib/exceptions.php';
+\OC::$CLASSPATH['OCA\Files_Sharing\Exceptions\BrokenPath'] = 'files_sharing/lib/exceptions.php';
+
+$application = new Application();
+$application->registerMountProviders();
+$application->setupPropagation();
\OCP\App::registerAdmin('files_sharing', 'settings-admin');
\OCA\Files_Sharing\Helper::registerHooks();
-OCP\Share::registerBackend('file', 'OC_Share_Backend_File');
-OCP\Share::registerBackend('folder', 'OC_Share_Backend_Folder', 'file');
+\OCP\Share::registerBackend('file', 'OC_Share_Backend_File');
+\OCP\Share::registerBackend('folder', 'OC_Share_Backend_Folder', 'file');
-OCP\Util::addScript('files_sharing', 'share');
-OCP\Util::addScript('files_sharing', 'external');
+\OCP\Util::addScript('files_sharing', 'share');
+\OCP\Util::addScript('files_sharing', 'external');
// FIXME: registering a job here will cause additional useless SQL queries
// when the route is not cron.php, needs a better way
diff --git a/apps/files_sharing/appinfo/application.php b/apps/files_sharing/appinfo/application.php
new file mode 100644
index 0000000..6848c9e
--- /dev/null
+++ b/apps/files_sharing/appinfo/application.php
@@ -0,0 +1,51 @@
+<?php
+/**
+ * Copyright (c) 2015 Robin Appelman <icewind at owncloud.com>
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+
+namespace OCA\Files_Sharing\Appinfo;
+
+use OCA\Files_Sharing\MountProvider;
+use OCA\Files_Sharing\Propagation\PropagationManager;
+use OCP\AppFramework\App;
+use \OCP\IContainer;
+
+class Application extends App {
+ public function __construct(array $urlParams = array()) {
+ parent::__construct('files_sharing', $urlParams);
+ $container = $this->getContainer();
+
+ $container->registerService('MountProvider', function (IContainer $c) {
+ /** @var \OCP\IServerContainer $server */
+ $server = $c->query('ServerContainer');
+ return new MountProvider(
+ $server->getConfig(),
+ $c->query('PropagationManager')
+ );
+ });
+
+ $container->registerService('PropagationManager', function (IContainer $c) {
+ /** @var \OCP\IServerContainer $server */
+ $server = $c->query('ServerContainer');
+ return new PropagationManager(
+ $server->getUserSession(),
+ $server->getConfig()
+ );
+ });
+ }
+
+ public function registerMountProviders() {
+ /** @var \OCP\IServerContainer $server */
+ $server = $this->getContainer()->query('ServerContainer');
+ $mountProviderCollection = $server->getMountProviderCollection();
+ $mountProviderCollection->registerProvider($this->getContainer()->query('MountProvider'));
+ }
+
+ public function setupPropagation() {
+ $propagationManager = $this->getContainer()->query('PropagationManager');
+ \OCP\Util::connectHook('OC_Filesystem', 'setup', $propagationManager, 'globalSetup');
+ }
+}
diff --git a/apps/files_sharing/appinfo/routes.php b/apps/files_sharing/appinfo/routes.php
index 9ac3a1f..db4566e 100644
--- a/apps/files_sharing/appinfo/routes.php
+++ b/apps/files_sharing/appinfo/routes.php
@@ -25,9 +25,6 @@
*/
namespace OCA\Files_Sharing\AppInfo;
-use OCA\Files_Sharing\Application;
-use OCP\API;
-
$application = new Application();
$application->registerRoutes($this, [
'resources' => [
diff --git a/apps/files_sharing/lib/helper.php b/apps/files_sharing/lib/helper.php
index 5b5525e..05b0352 100644
--- a/apps/files_sharing/lib/helper.php
+++ b/apps/files_sharing/lib/helper.php
@@ -30,9 +30,7 @@ namespace OCA\Files_Sharing;
class Helper {
public static function registerHooks() {
- \OCP\Util::connectHook('OC_Filesystem', 'setup', '\OC\Files\Storage\Shared', 'setup');
\OCP\Util::connectHook('OC_Filesystem', 'setup', '\OCA\Files_Sharing\External\Manager', 'setup');
- \OCP\Util::connectHook('OC_Filesystem', 'post_write', '\OC\Files\Cache\Shared_Updater', 'writeHook');
\OCP\Util::connectHook('OC_Filesystem', 'delete', '\OC\Files\Cache\Shared_Updater', 'deleteHook');
\OCP\Util::connectHook('OC_Filesystem', 'post_rename', '\OC\Files\Cache\Shared_Updater', 'renameHook');
\OCP\Util::connectHook('OC_Filesystem', 'post_delete', '\OCA\Files_Sharing\Hooks', 'unshareChildren');
diff --git a/apps/files_sharing/lib/mountprovider.php b/apps/files_sharing/lib/mountprovider.php
new file mode 100644
index 0000000..0ba44ec
--- /dev/null
+++ b/apps/files_sharing/lib/mountprovider.php
@@ -0,0 +1,70 @@
+<?php
+/**
+ * Copyright (c) 2015 Robin Appelman <icewind at owncloud.com>
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+
+namespace OCA\Files_Sharing;
+
+use OCA\Files_Sharing\Propagation\PropagationManager;
+use OCP\Files\Config\IMountProvider;
+use OCP\Files\Storage\IStorageFactory;
+use OCP\IConfig;
+use OCP\IUser;
+
+class MountProvider implements IMountProvider {
+ /**
+ * @var \OCP\IConfig
+ */
+ protected $config;
+
+ /**
+ * @var \OCA\Files_Sharing\Propagation\PropagationManager
+ */
+ protected $propagationManager;
+
+ /**
+ * @param \OCP\IConfig $config
+ * @param \OCA\Files_Sharing\Propagation\PropagationManager $propagationManager
+ */
+ function __construct(IConfig $config, PropagationManager $propagationManager) {
+ $this->config = $config;
+ $this->propagationManager = $propagationManager;
+ }
+
+
+ /**
+ * Get all mountpoints applicable for the user
+ *
+ * @param \OCP\IUser $user
+ * @param \OCP\Files\Storage\IStorageFactory $storageFactory
+ * @return \OCP\Files\Mount\IMountPoint[]
+ */
+ public function getMountsForUser(IUser $user, IStorageFactory $storageFactory) {
+ $shares = \OCP\Share::getItemsSharedWithUser('file', $user->getUID());
+ $propagator = $this->propagationManager->getSharePropagator($user->getUID());
+ $propagator->propagateDirtyMountPoints($shares);
+ $shares = array_filter($shares, function ($share) {
+ return $share['permissions'] > 0;
+ });
+ return array_map(function ($share) use ($user, $storageFactory) {
+ // for updating etags for the share owner when we make changes to this share.
+ $ownerPropagator = $this->propagationManager->getChangePropagator($share['uid_owner']);
+
+ // for updating our etags when changes are made to the share from the owners side (probably indirectly by us trough another share)
+ $this->propagationManager->listenToOwnerChanges($share['uid_owner'], $user->getUID());
+ return new SharedMount(
+ '\OC\Files\Storage\Shared',
+ '/' . $user->getUID() . '/' . $share['file_target'],
+ array(
+ 'propagator' => $ownerPropagator,
+ 'share' => $share,
+ 'user' => $user->getUID()
+ ),
+ $storageFactory
+ );
+ }, $shares);
+ }
+}
diff --git a/apps/files_sharing/lib/propagation/changewatcher.php b/apps/files_sharing/lib/propagation/changewatcher.php
new file mode 100644
index 0000000..fa5208b
--- /dev/null
+++ b/apps/files_sharing/lib/propagation/changewatcher.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Copyright (c) 2015 Robin Appelman <icewind at owncloud.com>
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+
+namespace OCA\Files_Sharing\Propagation;
+
+use OC\Files\Cache\ChangePropagator;
+use OC\Files\View;
+use OCA\Files_Sharing\SharedMount;
+
+/**
+ * Watch for changes made in a shared mount and propagate the changes to the share owner
+ */
+class ChangeWatcher {
+ /**
+ * The user view for the logged in user
+ *
+ * @var \OC\Files\View
+ */
+ private $baseView;
+
+ function __construct(View $baseView) {
+ $this->baseView = $baseView;
+ }
+
+
+ public function writeHook($params) {
+ $path = $params['path'];
+ $fullPath = $this->baseView->getAbsolutePath($path);
+ $mount = $this->baseView->getMount($path);
+ if ($mount instanceof SharedMount) {
+ $this->propagateForOwner($mount->getShare(), $mount->getInternalPath($fullPath), $mount->getOwnerPropagator());
+ }
+ }
+
+ /**
+ * @param array $share
+ * @param string $internalPath
+ * @param \OC\Files\Cache\ChangePropagator $propagator
+ */
+ private function propagateForOwner($share, $internalPath, ChangePropagator $propagator) {
+ // note that we have already set up the filesystem for the owner when mounting the share
+ $view = new View('/' . $share['uid_owner'] . '/files');
+
+ $shareRootPath = $view->getPath($share['item_source']);
+ if ($shareRootPath) {
+ $path = $shareRootPath . '/' . $internalPath;
+ $propagator->addChange($path);
+ $propagator->propagateChanges();
+ }
+ }
+}
diff --git a/apps/files_sharing/lib/propagation/propagationmanager.php b/apps/files_sharing/lib/propagation/propagationmanager.php
new file mode 100644
index 0000000..bf530d3
--- /dev/null
+++ b/apps/files_sharing/lib/propagation/propagationmanager.php
@@ -0,0 +1,113 @@
+<?php
+/**
+ * Copyright (c) 2015 Robin Appelman <icewind at owncloud.com>
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+
+namespace OCA\Files_Sharing\Propagation;
+
+use OC\Files\Filesystem;
+use OC\Files\View;
+use OCP\IConfig;
+use OCP\IUserSession;
+
+
+/**
+ * Keep track of all change and share propagators by owner
+ */
+class PropagationManager {
+ /**
+ * @var \OCP\IUserSession
+ */
+ private $userSession;
+
+ /**
+ * @var \OCP\IConfig
+ */
+ private $config;
+
+ /**
+ * Change propagators for share owner
+ *
+ * @var \OC\Files\Cache\ChangePropagator[]
+ */
+ private $changePropagators = [];
+
+ /**
+ * Recipient propagators
+ *
+ * @var \OCA\Files_Sharing\Propagation\RecipientPropagator[]
+ */
+ private $sharePropagators = [];
+
+ private $globalSetupDone = false;
+
+ function __construct(IUserSession $userSession, IConfig $config) {
+ $this->userSession = $userSession;
+ $this->config = $config;
+ }
+
+ /**
+ * @param string $user
+ * @return \OC\Files\Cache\ChangePropagator
+ */
+ public function getChangePropagator($user) {
+ $activeUser = $this->userSession->getUser();
+
+ // for the local user we want to propagator from the active view, not any cached one
+ if ($activeUser && $activeUser->getUID() === $user && Filesystem::getView() instanceof View) {
+ // it's important that we take the existing propagator here to make sure we can listen to external changes
+ $this->changePropagators[$user] = Filesystem::getView()->getUpdater()->getPropagator();
+ }
+ if (isset($this->changePropagators[$user])) {
+ return $this->changePropagators[$user];
+ }
+ $view = new View('/' . $user . '/files');
+ $this->changePropagators[$user] = $view->getUpdater()->getPropagator();
+ return $this->changePropagators[$user];
+ }
+
+ /**
+ * @param string $user
+ * @return \OCA\Files_Sharing\Propagation\RecipientPropagator
+ */
+ public function getSharePropagator($user) {
+ if (isset($this->sharePropagators[$user])) {
+ return $this->sharePropagators[$user];
+ }
+ $this->sharePropagators[$user] = new RecipientPropagator($user, $this->getChangePropagator($user), $this->config);
+ return $this->sharePropagators[$user];
+ }
+
+ /**
+ * Attach the propagator to the change propagator of a user to listen to changes made to files shared by the user
+ *
+ * @param string $shareOwner
+ * @param string $user
+ */
+ public function listenToOwnerChanges($shareOwner, $user) {
+ $sharePropagator = $this->getSharePropagator($user);
+ $ownerPropagator = $this->getChangePropagator($shareOwner);
+ $sharePropagator->attachToPropagator($ownerPropagator, $shareOwner);
+ }
+
+ /**
+ * To be called from setupFS trough a hook
+ *
+ * Sets up listening to changes made to shares owned by the current user
+ */
+ public function globalSetup() {
+ $user = $this->userSession->getUser();
+ if (!$user) {
+ return;
+ }
+ $watcher = new ChangeWatcher(Filesystem::getView());
+
+ // for marking shares owned by the active user as dirty when a file inside them changes
+ $this->listenToOwnerChanges($user->getUID(), $user->getUID());
+ \OC_Hook::connect('OC_Filesystem', 'write', $watcher, 'writeHook');
+ \OC_Hook::connect('OC_Filesystem', 'delete', $watcher, 'writeHook');
+ }
+}
diff --git a/apps/files_sharing/lib/propagation/recipientpropagator.php b/apps/files_sharing/lib/propagation/recipientpropagator.php
new file mode 100644
index 0000000..da71612
--- /dev/null
+++ b/apps/files_sharing/lib/propagation/recipientpropagator.php
@@ -0,0 +1,108 @@
+<?php
+/**
+ * Copyright (c) 2015 Robin Appelman <icewind at owncloud.com>
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+
+namespace OCA\Files_Sharing\Propagation;
+
+use OC\Files\Cache\ChangePropagator;
+use OC\Share\Share;
+
+/**
+ * Propagate etags for share recipients
+ */
+class RecipientPropagator {
+ /**
+ * @var string
+ */
+ protected $userId;
+
+ /**
+ * @var \OC\Files\Cache\ChangePropagator
+ */
+ protected $changePropagator;
+
+ /**
+ * @var \OCP\IConfig
+ */
+ protected $config;
+
+ /**
+ * @param string $userId current user, must match the propagator's
+ * user
+ * @param \OC\Files\Cache\ChangePropagator $changePropagator change propagator
+ * initialized with a view for $user
+ * @param \OCP\IConfig $config
+ */
+ public function __construct($userId, $changePropagator, $config) {
+ $this->userId = $userId;
+ $this->changePropagator = $changePropagator;
+ $this->config = $config;
+ }
+
+ /**
+ * Propagate the etag changes for all shares marked as dirty and mark the shares as clean
+ *
+ * @param array $shares the shares for the users
+ * @param int $time
+ */
+ public function propagateDirtyMountPoints(array $shares, $time = null) {
+ if ($time === null) {
+ $time = time();
+ }
+ $dirtyShares = $this->getDirtyShares($shares);
+ foreach ($dirtyShares as $share) {
+ $this->changePropagator->addChange($share['file_target']);
+ }
+ if (count($dirtyShares)) {
+ $this->config->setUserValue($this->userId, 'files_sharing', 'last_propagate', $time);
+ $this->changePropagator->propagateChanges($time);
+ }
+ }
+
+ /**
+ * Get all shares we need to update the etag for
+ *
+ * @param array $shares the shares for the users
+ * @return string[]
+ */
+ protected function getDirtyShares($shares) {
+ $dirty = [];
+ $userTime = $this->config->getUserValue($this->userId, 'files_sharing', 'last_propagate', 0);
+ foreach ($shares as $share) {
+ $updateTime = $this->config->getAppValue('files_sharing', $share['id'], 0);
+ if ($updateTime >= $userTime) {
+ $dirty[] = $share;
+ }
+ }
+ return $dirty;
+ }
+
+ /**
+ * @param array $share
+ * @param int $time
+ */
+ public function markDirty($share, $time = null) {
+ if ($time === null) {
+ $time = time();
+ }
+ $this->config->setAppValue('files_sharing', $share['id'], $time);
+ }
+ /**
+ * Listen on the propagator for updates made to shares owned by a user
+ *
+ * @param \OC\Files\Cache\ChangePropagator $propagator
+ * @param string $owner
+ */
+ public function attachToPropagator(ChangePropagator $propagator, $owner) {
+ $propagator->listen('\OC\Files', 'propagate', function ($path, $entry) use ($owner) {
+ $shares = Share::getAllSharesForFileId($entry['fileid']);
+ foreach ($shares as $share) {
+ $this->markDirty($share, time());
+ }
+ });
+ }
+}
diff --git a/apps/files_sharing/lib/sharedmount.php b/apps/files_sharing/lib/sharedmount.php
index da00549..fbf8d05 100644
--- a/apps/files_sharing/lib/sharedmount.php
+++ b/apps/files_sharing/lib/sharedmount.php
@@ -35,8 +35,14 @@ class SharedMount extends MountPoint implements MoveableMount {
*/
protected $storage = null;
+ /**
+ * @var \OC\Files\Cache\ChangePropagator
+ */
+ protected $ownerPropagator;
+
public function __construct($storage, $mountpoint, $arguments = null, $loader = null) {
// first update the mount point before creating the parent
+ $this->ownerPropagator = $arguments['propagator'];
$newMountPoint = $this->verifyMountPoint($arguments['share'], $arguments['user']);
$absMountPoint = '/' . $arguments['user'] . '/files' . $newMountPoint;
parent::__construct($storage, $absMountPoint, $arguments, $loader);
@@ -174,4 +180,16 @@ class SharedMount extends MountPoint implements MoveableMount {
return $result;
}
+
+ public function getShare() {
+ $this->getStorage(); //ensure it exists
+ return $this->storage->getShare();
+ }
+
+ /**
+ * @return \OC\Files\Cache\ChangePropagator
+ */
+ public function getOwnerPropagator() {
+ return $this->ownerPropagator;
+ }
}
diff --git a/apps/files_sharing/lib/sharedstorage.php b/apps/files_sharing/lib/sharedstorage.php
index 8c2f03b..bc01465 100644
--- a/apps/files_sharing/lib/sharedstorage.php
+++ b/apps/files_sharing/lib/sharedstorage.php
@@ -28,8 +28,12 @@
*/
namespace OC\Files\Storage;
+
+use OC\Files\Cache\ChangePropagator;
use OC\Files\Filesystem;
+use OC\Files\View;
use OCA\Files_Sharing\ISharedStorage;
+use OCA\Files_Sharing\Propagator;
use OCA\Files_Sharing\SharedMount;
/**
@@ -47,6 +51,7 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
/**
* get id of the mount point
+ *
* @return string
*/
public function getId() {
@@ -55,14 +60,16 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
/**
* get file cache of the shared item source
+ *
* @return int
*/
public function getSourceId() {
- return (int) $this->share['file_source'];
+ return (int)$this->share['file_source'];
}
/**
* Get the source file path, permissions, and owner for a shared file
+ *
* @param string $target Shared target file path
* @return Returns array with the keys path, permissions, and owner or false if not found
*/
@@ -86,6 +93,7 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
/**
* Get the source file path for a shared file
+ *
* @param string $target Shared target file path
* @return string|false source file path or false if not found
*/
@@ -109,6 +117,7 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
/**
* Get the permissions granted for a shared file
+ *
* @param string $target Shared target file path
* @return int CRUDS permissions granted
*/
@@ -138,13 +147,14 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
/**
* Delete the directory if DELETE permission is granted
+ *
* @param string $path
* @return boolean
*/
public function rmdir($path) {
// never delete a share mount point
- if(empty($path)) {
+ if (empty($path)) {
return false;
}
@@ -277,6 +287,7 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
/**
* Delete the file if DELETE permission is granted
+ *
* @param string $path
* @return boolean
*/
@@ -426,37 +437,6 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
return false;
}
- public static function setup($options) {
- $user = $options['user'];
- $shares = \OCP\Share::getItemsSharedWithUser('file', $user);
- $manager = Filesystem::getMountManager();
- $loader = Filesystem::getLoader();
- if (
- !isset(self::$isInitialized[$user]) && (
- !\OCP\User::isLoggedIn()
- || \OCP\User::getUser() != $options['user']
- || $shares
- )
- ) {
- foreach ($shares as $share) {
- // don't mount shares where we have no permissions
- if ($share['permissions'] > 0) {
- $mount = new SharedMount(
- '\OC\Files\Storage\Shared',
- $options['user_dir'] . '/' . $share['file_target'],
- array(
- 'share' => $share,
- 'user' => $user
- ),
- $loader
- );
- $manager->addMount($mount);
- }
- }
- }
- self::$isInitialized[$user] = true;
- }
-
/**
* return mount point of share, relative to data/user/files
*
@@ -476,6 +456,7 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
/**
* does the group share already has a user specific unique name
+ *
* @return bool
*/
public function uniqueNameSet() {
@@ -493,6 +474,7 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
/**
* get share ID
+ *
* @return integer unique share ID
*/
public function getShareId() {
@@ -501,6 +483,7 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
/**
* get the user who shared the file
+ *
* @return string
*/
public function getSharedFrom() {
@@ -516,6 +499,7 @@ class Shared extends \OC\Files\Storage\Common implements ISharedStorage {
/**
* return share type, can be "file" or "folder"
+ *
* @return string
*/
public function getItemType() {
diff --git a/apps/files_sharing/lib/updater.php b/apps/files_sharing/lib/updater.php
index 322c031..45cf662 100644
--- a/apps/files_sharing/lib/updater.php
+++ b/apps/files_sharing/lib/updater.php
@@ -50,47 +50,9 @@ class Shared_Updater {
}
/**
- * Correct the parent folders' ETags for all users shared the file at $target
- *
- * @param string $target
- */
- static public function correctFolders($target) {
-
- // ignore part files
- if (pathinfo($target, PATHINFO_EXTENSION) === 'part') {
- return false;
- }
-
- // Correct Shared folders of other users shared with
- $shares = \OCA\Files_Sharing\Helper::getSharesFromItem($target);
-
- foreach ($shares as $share) {
- if ((int)$share['share_type'] === \OCP\Share::SHARE_TYPE_USER) {
- self::correctUsersFolder($share['share_with'], $share['file_target']);
- } elseif ((int)$share['share_type'] === \OCP\Share::SHARE_TYPE_GROUP) {
- $users = \OC_Group::usersInGroup($share['share_with']);
- foreach ($users as $user) {
- self::correctUsersFolder($user, $share['file_target']);
- }
- } else { //unique name for group share
- self::correctUsersFolder($share['share_with'], $share['file_target']);
- }
- }
- }
-
- /**
- * @param array $params
- */
- static public function writeHook($params) {
- self::correctFolders($params['path']);
- }
-
- /**
* @param array $params
*/
static public function renameHook($params) {
- self::correctFolders($params['newpath']);
- self::correctFolders(pathinfo($params['oldpath'], PATHINFO_DIRNAME));
self::renameChildren($params['oldpath'], $params['newpath']);
}
@@ -99,7 +61,6 @@ class Shared_Updater {
*/
static public function deleteHook($params) {
$path = $params['path'];
- self::correctFolders($path);
}
/**
diff --git a/apps/files_sharing/tests/propagation.php b/apps/files_sharing/tests/propagation.php
index 1949f78..c42dccc 100644
--- a/apps/files_sharing/tests/propagation.php
+++ b/apps/files_sharing/tests/propagation.php
@@ -242,4 +242,52 @@ class Propagation extends TestCase {
$newRootInfo = $view1->getFileInfo('');
$this->assertNotEquals($rootInfo->getEtag(), $newRootInfo->getEtag());
}
+
+ public function testSizePropagationWhenOwnerChangesFile() {
+ /**
+ * @var \OC\Files\View $recipientView
+ * @var \OC\Files\View $ownerView
+ */
+ list($recipientView, $ownerView) = $this->setupViews();
+ $sharedFolderInfo = $ownerView->getFileInfo('/sharedfolder', false);
+ \OCP\Share::shareItem('folder', $sharedFolderInfo->getId(), \OCP\Share::SHARE_TYPE_USER, self::TEST_FILES_SHARING_API_USER1, 31);
+ $ownerRootInfo = $ownerView->getFileInfo('', false);
+ $this->loginAsUser(self::TEST_FILES_SHARING_API_USER1);
+ $this->assertTrue($recipientView->file_exists('/sharedfolder/subfolder/foo.txt'));
+ $recipientRootInfo = $recipientView->getFileInfo('', false);
+ // when file changed as owner
+ $this->loginAsUser(self::TEST_FILES_SHARING_API_USER2);
+ $ownerView->file_put_contents('/sharedfolder/subfolder/foo.txt', 'foobar');
+ // size of recipient's root stays the same
+ $this->loginAsUser(self::TEST_FILES_SHARING_API_USER1);
+ $newRecipientRootInfo = $recipientView->getFileInfo('', false);
+ $this->assertEquals($recipientRootInfo->getSize(), $newRecipientRootInfo->getSize());
+ // size of owner's root increases
+ $this->loginAsUser(self::TEST_FILES_SHARING_API_USER2);
+ $newOwnerRootInfo = $ownerView->getFileInfo('', false);
+ $this->assertEquals($ownerRootInfo->getSize() + 3, $newOwnerRootInfo->getSize());
+ }
+
+ public function testSizePropagationWhenRecipientChangesFile() {
+ /**
+ * @var \OC\Files\View $recipientView
+ * @var \OC\Files\View $ownerView
+ */
+ list($recipientView, $ownerView) = $this->setupViews();
+ $sharedFolderInfo = $ownerView->getFileInfo('/sharedfolder', false);
+ \OCP\Share::shareItem('folder', $sharedFolderInfo->getId(), \OCP\Share::SHARE_TYPE_USER, self::TEST_FILES_SHARING_API_USER1, 31);
+ $ownerRootInfo = $ownerView->getFileInfo('', false);
+ $this->loginAsUser(self::TEST_FILES_SHARING_API_USER1);
+ $this->assertTrue($recipientView->file_exists('/sharedfolder/subfolder/foo.txt'));
+ $recipientRootInfo = $recipientView->getFileInfo('', false);
+ // when file changed as recipient
+ $recipientView->file_put_contents('/sharedfolder/subfolder/foo.txt', 'foobar');
+ // size of recipient's root stays the same
+ $newRecipientRootInfo = $recipientView->getFileInfo('', false);
+ $this->assertEquals($recipientRootInfo->getSize(), $newRecipientRootInfo->getSize());
+ // size of owner's root increases
+ $this->loginAsUser(self::TEST_FILES_SHARING_API_USER2);
+ $newOwnerRootInfo = $ownerView->getFileInfo('', false);
+ $this->assertEquals($ownerRootInfo->getSize() + 3, $newOwnerRootInfo->getSize());
+ }
}
diff --git a/apps/files_sharing/tests/testcase.php b/apps/files_sharing/tests/testcase.php
index b9f8658..5cae54f 100644
--- a/apps/files_sharing/tests/testcase.php
+++ b/apps/files_sharing/tests/testcase.php
@@ -31,6 +31,7 @@ namespace OCA\Files_Sharing\Tests;
use OC\Files\Filesystem;
use OCA\Files\Share;
+use OCA\Files_Sharing\Appinfo\Application;
/**
* Class Test_Files_Sharing_Base
@@ -57,6 +58,10 @@ abstract class TestCase extends \Test\TestCase {
public static function setUpBeforeClass() {
parent::setUpBeforeClass();
+ $application = new Application();
+ $application->registerMountProviders();
+ $application->setupPropagation();
+
// reset backend
\OC_User::clearBackends();
\OC_Group::clearBackends();
@@ -64,7 +69,6 @@ abstract class TestCase extends \Test\TestCase {
// clear share hooks
\OC_Hook::clear('OCP\\Share');
\OC::registerShareHooks();
- \OCP\Util::connectHook('OC_Filesystem', 'setup', '\OC\Files\Storage\Shared', 'setup');
// create users
$backend = new \OC_User_Dummy();
@@ -147,6 +151,7 @@ abstract class TestCase extends \Test\TestCase {
\OC::$server->getUserSession()->setUser(null);
\OC\Files\Filesystem::tearDown();
\OC::$server->getUserSession()->login($user, $password);
+
\OC_Util::setupFS($user);
}
diff --git a/lib/private/share/share.php b/lib/private/share/share.php
index 63bba06..d18bdff 100644
--- a/lib/private/share/share.php
+++ b/lib/private/share/share.php
@@ -2518,6 +2518,7 @@ class Share extends \OC\Share\Constants {
$enforcePassword = $config->getAppValue('core', 'shareapi_enforce_links_password', 'no');
return ($enforcePassword === "yes") ? true : false;
}
+
/**
* Get all share entries, including non-unique group items
*
@@ -2530,4 +2531,15 @@ class Share extends \OC\Share\Constants {
return $result->fetchAll();
}
+ /**
+ * Get all share entries, including non-unique group items for a file
+ *
+ * @param int $id
+ * @return array
+ */
+ public static function getAllSharesForFileId($id) {
+ $query = 'SELECT * FROM `*PREFIX*share` WHERE `file_source` = ?';
+ $result = \OC::$server->getDatabaseConnection()->executeQuery($query, [$id]);
+ return $result->fetchAll();
+ }
}
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-owncloud/owncloud.git
More information about the Pkg-owncloud-commits
mailing list