[Pkg-owncloud-commits] [owncloud] 39/273: make sure that during share and unshare the etags get propagated correctly

David Prévot taffit at moszumanska.debian.org
Fri Jul 4 03:12:55 UTC 2014


This is an automated email from the git hooks/post-receive script.

taffit pushed a commit to branch master
in repository owncloud.

commit a0b85fc5e4a56ff553f224083cbdf87cd05ec55a
Author: Bjoern Schiessle <schiessle at owncloud.com>
Date:   Tue Jun 24 17:04:27 2014 +0200

    make sure that during share and unshare the etags get propagated correctly
---
 apps/files_sharing/appinfo/app.php   |   4 ++
 apps/files_sharing/lib/updater.php   |  62 ++++++++++++++++++++
 apps/files_sharing/tests/updater.php | 106 +++++++++++++++++++++++++++++++++++
 lib/private/share/helper.php         |  22 ++++++--
 lib/private/share/share.php          |  60 +++++++++++++++++---
 5 files changed, 242 insertions(+), 12 deletions(-)

diff --git a/apps/files_sharing/appinfo/app.php b/apps/files_sharing/appinfo/app.php
index a4a0a57..412ca66 100644
--- a/apps/files_sharing/appinfo/app.php
+++ b/apps/files_sharing/appinfo/app.php
@@ -28,6 +28,10 @@ OCP\Util::addScript('files_sharing', 'external');
 \OC_Hook::connect('OC_Filesystem', 'post_rename', '\OC\Files\Cache\Shared_Updater', 'renameHook');
 \OC_Hook::connect('OC_Appconfig', 'post_set_value', '\OCA\Files\Share\Maintainer', 'configChangeHook');
 
+\OCP\Util::connectHook('OCP\Share', 'post_shared', '\OC\Files\Cache\Shared_Updater', 'postShareHook');
+\OCP\Util::connectHook('OCP\Share', 'post_unshare', '\OC\Files\Cache\Shared_Updater', 'postUnshareHook');
+\OCP\Util::connectHook('OCP\Share', 'post_unshareFromSelf', '\OC\Files\Cache\Shared_Updater', 'postUnshareFromSelfHook');
+
 OC_FileProxy::register(new OCA\Files\Share\Proxy());
 
 \OCA\Files\App::getNavigationManager()->add(
diff --git a/apps/files_sharing/lib/updater.php b/apps/files_sharing/lib/updater.php
index 5cb2b63..e114c3b 100644
--- a/apps/files_sharing/lib/updater.php
+++ b/apps/files_sharing/lib/updater.php
@@ -133,6 +133,68 @@ class Shared_Updater {
 	}
 
 	/**
+	 * update etags if a file was shared
+	 * @param array $params
+	 */
+	static public function postShareHook($params) {
+
+		if ($params['itemType'] === 'folder' || $params['itemType'] === 'file') {
+
+			$shareWith = $params['shareWith'];
+			$shareType = $params['shareType'];
+
+			if ($shareType === \OCP\Share::SHARE_TYPE_USER) {
+				self::correctUsersFolder($shareWith, '/');
+			} elseif ($shareType === \OCP\Share::SHARE_TYPE_GROUP) {
+				foreach (\OC_Group::usersInGroup($shareWith) as $user) {
+					self::correctUsersFolder($user, '/');
+				}
+			}
+		}
+	}
+
+	/**
+	 * update etags if a file was unshared
+	 *
+	 * @param array $params
+	 */
+	static public function postUnshareHook($params) {
+
+		if ($params['itemType'] === 'file' || $params['itemType'] === 'folder') {
+
+			$deletedShares = isset($params['deletedShares']) ? $params['deletedShares'] : array();
+
+			foreach ($deletedShares as $share) {
+				if ($share['shareType'] === \OCP\Share::SHARE_TYPE_GROUP) {
+					foreach (\OC_Group::usersInGroup($share['shareWith']) as $user) {
+						self::correctUsersFolder($user, dirname($share['fileTarget']));
+					}
+				} else {
+					self::correctUsersFolder($share['shareWith'], dirname($share['fileTarget']));
+				}
+			}
+		}
+	}
+
+	/**
+	 * update etags if file was unshared from self
+	 * @param array $params
+	 */
+	static public function postUnshareFromSelfHook($params) {
+		if ($params['itemType'] === 'file' || $params['itemType'] === 'folder') {
+			foreach ($params['unsharedItems'] as $item) {
+				if ($item['shareType'] === \OCP\Share::SHARE_TYPE_GROUP) {
+					foreach (\OC_Group::usersInGroup($item['shareWith']) as $user) {
+						self::correctUsersFolder($user, dirname($item['fileTarget']));
+					}
+				} else {
+					self::correctUsersFolder($item['shareWith'], dirname($item['fileTarget']));
+				}
+			}
+		}
+	}
+
+	/**
 	 * clean up oc_share table from files which are no longer exists
 	 *
 	 * This fixes issues from updates from files_sharing < 0.3.5.6 (ownCloud 4.5)
diff --git a/apps/files_sharing/tests/updater.php b/apps/files_sharing/tests/updater.php
index 8183e70..c0099b4 100644
--- a/apps/files_sharing/tests/updater.php
+++ b/apps/files_sharing/tests/updater.php
@@ -104,6 +104,112 @@ class Test_Files_Sharing_Updater extends Test_Files_Sharing_Base {
 		if ($status === false) {
 			\OC_App::disable('files_trashbin');
 		}
+		// cleanup
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER1);
+		$result = \OCP\Share::unshare('folder', $fileinfo->getId(), \OCP\Share::SHARE_TYPE_USER, self::TEST_FILES_SHARING_API_USER2);
+		$this->assertTrue($result);
+	}
+
+	/**
+	 * if a file gets shared the etag for the recipients root should change
+	 */
+	function testShareFile() {
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER2);
+
+		$beforeShare = \OC\Files\Filesystem::getFileInfo('');
+		$etagBeforeShare = $beforeShare->getEtag();
+
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER1);
+		$fileinfo = \OC\Files\Filesystem::getFileInfo($this->folder);
+		$result = \OCP\Share::shareItem('folder', $fileinfo->getId(), \OCP\Share::SHARE_TYPE_USER, self::TEST_FILES_SHARING_API_USER2, 31);
+		$this->assertTrue($result);
+
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER2);
+
+		$afterShare = \OC\Files\Filesystem::getFileInfo('');
+		$etagAfterShare = $afterShare->getEtag();
+
+		$this->assertTrue(is_string($etagBeforeShare));
+		$this->assertTrue(is_string($etagAfterShare));
+		$this->assertTrue($etagBeforeShare !== $etagAfterShare);
+
+		// cleanup
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER1);
+		$result = \OCP\Share::unshare('folder', $fileinfo->getId(), \OCP\Share::SHARE_TYPE_USER, self::TEST_FILES_SHARING_API_USER2);
+		$this->assertTrue($result);
+	}
+
+	/**
+	 * if a file gets unshared by the owner the etag for the recipients root should change
+	 */
+	function testUnshareFile() {
+
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER1);
+		$fileinfo = \OC\Files\Filesystem::getFileInfo($this->folder);
+		$result = \OCP\Share::shareItem('folder', $fileinfo->getId(), \OCP\Share::SHARE_TYPE_USER, self::TEST_FILES_SHARING_API_USER2, 31);
+		$this->assertTrue($result);
+
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER2);
+
+		$beforeUnshare = \OC\Files\Filesystem::getFileInfo('');
+		$etagBeforeUnshare = $beforeUnshare->getEtag();
+
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER1);
+		$result = \OCP\Share::unshare('folder', $fileinfo->getId(), \OCP\Share::SHARE_TYPE_USER, self::TEST_FILES_SHARING_API_USER2);
+		$this->assertTrue($result);
+
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER2);
+
+		$afterUnshare = \OC\Files\Filesystem::getFileInfo('');
+		$etagAfterUnshare = $afterUnshare->getEtag();
+
+		$this->assertTrue(is_string($etagBeforeUnshare));
+		$this->assertTrue(is_string($etagAfterUnshare));
+		$this->assertTrue($etagBeforeUnshare !== $etagAfterUnshare);
+
+	}
+
+	/**
+	 * if a file gets unshared from self the etag for the recipients root should change
+	 */
+	function testUnshareFromSelfFile() {
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER1);
+		$fileinfo = \OC\Files\Filesystem::getFileInfo($this->folder);
+		$result = \OCP\Share::shareItem('folder', $fileinfo->getId(), \OCP\Share::SHARE_TYPE_USER, self::TEST_FILES_SHARING_API_USER2, 31);
+		$this->assertTrue($result);
+
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER2);
+
+		$result = \OCP\Share::shareItem('folder', $fileinfo->getId(), \OCP\Share::SHARE_TYPE_USER, self::TEST_FILES_SHARING_API_USER3, 31);
+
+		$beforeUnshareUser2 = \OC\Files\Filesystem::getFileInfo('');
+		$etagBeforeUnshareUser2 = $beforeUnshareUser2->getEtag();
+
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER3);
+
+		$beforeUnshareUser3 = \OC\Files\Filesystem::getFileInfo('');
+		$etagBeforeUnshareUser3 = $beforeUnshareUser3->getEtag();
+
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER2);
+
+		$result = \OC\Files\Filesystem::unlink($this->folder);
+		$this->assertTrue($result);
+
+		$afterUnshareUser2 = \OC\Files\Filesystem::getFileInfo('');
+		$etagAfterUnshareUser2 = $afterUnshareUser2->getEtag();
+
+		$this->loginHelper(self::TEST_FILES_SHARING_API_USER3);
+
+		$afterUnshareUser3 = \OC\Files\Filesystem::getFileInfo('');
+		$etagAfterUnshareUser3 = $afterUnshareUser3->getEtag();
+
+		$this->assertTrue(is_string($etagBeforeUnshareUser2));
+		$this->assertTrue(is_string($etagBeforeUnshareUser3));
+		$this->assertTrue(is_string($etagAfterUnshareUser2));
+		$this->assertTrue(is_string($etagAfterUnshareUser3));
+		$this->assertTrue($etagBeforeUnshareUser2 !== $etagAfterUnshareUser2);
+		$this->assertTrue($etagBeforeUnshareUser3 !== $etagAfterUnshareUser3);
+
 	}
 
 }
diff --git a/lib/private/share/helper.php b/lib/private/share/helper.php
index 71c6d85..46e3c28 100644
--- a/lib/private/share/helper.php
+++ b/lib/private/share/helper.php
@@ -149,17 +149,18 @@ class Helper extends \OC\Share\Constants {
 	 */
 	public static function delete($parent, $excludeParent = false, $uidOwner = null) {
 		$ids = array($parent);
+		$deletedItems = array();
 		$parents = array($parent);
 		while (!empty($parents)) {
 			$parents = "'".implode("','", $parents)."'";
 			// Check the owner on the first search of reshares, useful for
 			// finding and deleting the reshares by a single user of a group share
 			if (count($ids) == 1 && isset($uidOwner)) {
-				$query = \OC_DB::prepare('SELECT `id`, `uid_owner`, `item_type`, `item_target`, `parent`'
+				$query = \OC_DB::prepare('SELECT `id`, `share_with`, `item_type`, `share_type`, `item_target`, `file_target`, `parent`'
 					.' FROM `*PREFIX*share` WHERE `parent` IN ('.$parents.') AND `uid_owner` = ?');
 				$result = $query->execute(array($uidOwner));
 			} else {
-				$query = \OC_DB::prepare('SELECT `id`, `item_type`, `item_target`, `parent`, `uid_owner`'
+				$query = \OC_DB::prepare('SELECT `id`, `share_with`, `item_type`, `share_type`, `item_target`, `file_target`, `parent`, `uid_owner`'
 					.' FROM `*PREFIX*share` WHERE `parent` IN ('.$parents.')');
 				$result = $query->execute();
 			}
@@ -168,16 +169,29 @@ class Helper extends \OC\Share\Constants {
 			while ($item = $result->fetchRow()) {
 				$ids[] = $item['id'];
 				$parents[] = $item['id'];
+				$tmpItem = array(
+					'id' => $item['id'],
+					'shareWith' => $item['share_with'],
+					'itemTarget' => $item['item_target'],
+					'itemType' => $item['item_type'],
+					'shareType' => (int)$item['share_type'],
+				);
+				if (isset($item['file_target'])) {
+					$tmpItem['fileTarget'] = $item['file_target'];
+				}
+				$deletedItems[] = $tmpItem;
 			}
 		}
 		if ($excludeParent) {
 			unset($ids[0]);
 		}
 		if (!empty($ids)) {
-			$ids = "'".implode("','", $ids)."'";
-			$query = \OC_DB::prepare('DELETE FROM `*PREFIX*share` WHERE `id` IN ('.$ids.')');
+			$idList = "'".implode("','", $ids)."'";
+			$query = \OC_DB::prepare('DELETE FROM `*PREFIX*share` WHERE `id` IN ('.$idList.')');
 			$query->execute();
 		}
+
+		return $deletedItems;
 	}
 
 	/**
diff --git a/lib/private/share/share.php b/lib/private/share/share.php
index 26108a9..c06ea72 100644
--- a/lib/private/share/share.php
+++ b/lib/private/share/share.php
@@ -738,11 +738,24 @@ class Share extends \OC\Share\Constants {
 
 		$shares = $result->fetchAll();
 
+		$listOfUnsharedItems = array();
+
 		$itemUnshared = false;
 		foreach ($shares as $share) {
 			if ((int)$share['share_type'] === \OCP\Share::SHARE_TYPE_USER &&
 					$share['share_with'] === $uid) {
-				Helper::delete($share['id']);
+				$deletedShares = Helper::delete($share['id']);
+				$shareTmp = array(
+					'id' => $share['id'],
+					'shareWith' => $share['share_with'],
+					'itemTarget' => $share['item_target'],
+					'itemType' => $share['item_type'],
+					'shareType' => (int)$share['share_type'],
+				);
+				if (isset($share['file_target'])) {
+					$shareTmp['fileTarget'] = $share['file_target'];
+				}
+				$listOfUnsharedItems = array_merge($listOfUnsharedItems, $deletedShares, array($shareTmp));
 				$itemUnshared = true;
 				break;
 			} elseif ((int)$share['share_type'] === \OCP\Share::SHARE_TYPE_GROUP) {
@@ -764,13 +777,40 @@ class Share extends \OC\Share\Constants {
 				$groupShare['id'], self::$shareTypeGroupUserUnique,
 				\OC_User::getUser(), $groupShare['uid_owner'], 0, $groupShare['stime'], $groupShare['file_source'],
 				$groupShare['file_target']));
+			$shareTmp = array(
+				'id' => $groupShare['id'],
+				'shareWith' => $groupShare['share_with'],
+				'itemTarget' => $groupShare['item_target'],
+				'itemType' => $groupShare['item_type'],
+				'shareType' => (int)$groupShare['share_type'],
+				);
+			if (isset($groupShare['file_target'])) {
+				$shareTmp['fileTarget'] = $groupShare['file_target'];
+			}
+			$listOfUnsharedItems = array_merge($listOfUnsharedItems, array($groupShare));
 			$itemUnshared = true;
 		} elseif (!$itemUnshared && isset($uniqueGroupShare)) {
 			$query = \OC_DB::prepare('UPDATE `*PREFIX*share` SET `permissions` = ? WHERE `id` = ?');
 			$query->execute(array(0, $uniqueGroupShare['id']));
+			$shareTmp = array(
+				'id' => $uniqueGroupShare['id'],
+				'shareWith' => $uniqueGroupShare['share_with'],
+				'itemTarget' => $uniqueGroupShare['item_target'],
+				'itemType' => $uniqueGroupShare['item_type'],
+				'shareType' => (int)$uniqueGroupShare['share_type'],
+				);
+			if (isset($uniqueGroupShare['file_target'])) {
+				$shareTmp['fileTarget'] = $uniqueGroupShare['file_target'];
+			}
+			$listOfUnsharedItems = array_merge($listOfUnsharedItems, array($uniqueGroupShare));
 			$itemUnshared = true;
 		}
 
+		if ($itemUnshared) {
+			\OC_Hook::emit('OCP\Share', 'post_unshareFromSelf',
+					array('unsharedItems' => $listOfUnsharedItems, 'itemType' => $itemType));
+		}
+
 		return $itemUnshared;
 	}
 
@@ -967,19 +1007,23 @@ class Share extends \OC\Share\Constants {
 	protected static function unshareItem(array $item) {
 		// Pass all the vars we have for now, they may be useful
 		$hookParams = array(
+			'id'            => $item['id'],
 			'itemType'      => $item['item_type'],
 			'itemSource'    => $item['item_source'],
-			'fileSource'    => $item['file_source'],
-			'shareType'     => $item['share_type'],
+			'shareType'     => (int)$item['share_type'],
 			'shareWith'     => $item['share_with'],
 			'itemParent'    => $item['parent'],
 			'uidOwner'      => $item['uid_owner'],
 		);
+		if($item['item_type'] === 'file' || $item['item_type'] === 'folder') {
+			$hookParams['fileSource'] = $item['file_source'];
+			$hookParams['fileTarget'] = $item['file_target'];
+		}
 
-		\OC_Hook::emit('OCP\Share', 'pre_unshare', $hookParams + array(
-			'fileSource'	=> $item['file_source'],
-		));
-		Helper::delete($item['id']);
+		\OC_Hook::emit('OCP\Share', 'pre_unshare', $hookParams);
+		$deletedShares = Helper::delete($item['id']);
+		$deletedShares[] = $hookParams;
+		$hookParams['deletedShares'] = $deletedShares;
 		\OC_Hook::emit('OCP\Share', 'post_unshare', $hookParams);
 	}
 
@@ -1788,7 +1832,7 @@ class Share extends \OC\Share\Constants {
 			if (isset($uidOwner)) {
 				if ($fileDependent) {
 					$select = '`*PREFIX*share`.`id`, `item_type`, `item_source`, `*PREFIX*share`.`parent`,'
-							. ' `share_type`, `share_with`, `file_source`, `path`, `*PREFIX*share`.`permissions`, `stime`,'
+							. ' `share_type`, `share_with`, `file_source`, `file_target`, `path`, `*PREFIX*share`.`permissions`, `stime`,'
 							. ' `expiration`, `token`, `storage`, `mail_send`, `uid_owner`';
 				} else {
 					$select = '`id`, `item_type`, `item_source`, `parent`, `share_type`, `share_with`, `*PREFIX*share`.`permissions`,'

-- 
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