Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.
Common duplication problems, and corresponding solutions are:
Complex classes like Test_Share often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.
Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.
While breaking up the class, it is a good idea to analyze how other classes use Test_Share, and based on these observations, apply Extract Interface, too.
| 1 | <?php |
||
| 22 | class Test_Share extends \Test\TestCase { |
||
| 23 | |||
| 24 | protected $itemType; |
||
| 25 | protected $userBackend; |
||
| 26 | protected $user1; |
||
| 27 | protected $user2; |
||
| 28 | protected $user3; |
||
| 29 | protected $user4; |
||
| 30 | protected $user5; |
||
| 31 | protected $user6; |
||
| 32 | protected $groupAndUser; |
||
| 33 | protected $groupBackend; |
||
| 34 | protected $group1; |
||
| 35 | protected $group2; |
||
| 36 | protected $resharing; |
||
| 37 | protected $dateInFuture; |
||
| 38 | protected $dateInPast; |
||
| 39 | |||
| 40 | protected function setUp() { |
||
| 41 | parent::setUp(); |
||
| 42 | |||
| 43 | OC_User::clearBackends(); |
||
| 44 | OC_User::useBackend('dummy'); |
||
| 45 | $this->user1 = $this->getUniqueID('user1_'); |
||
| 46 | $this->user2 = $this->getUniqueID('user2_'); |
||
| 47 | $this->user3 = $this->getUniqueID('user3_'); |
||
| 48 | $this->user4 = $this->getUniqueID('user4_'); |
||
| 49 | $this->user5 = $this->getUniqueID('user5_'); |
||
| 50 | $this->user6 = $this->getUniqueID('user6_'); |
||
| 51 | $this->groupAndUser = $this->getUniqueID('groupAndUser_'); |
||
| 52 | OC_User::createUser($this->user1, 'pass'); |
||
| 53 | OC_User::createUser($this->user2, 'pass'); |
||
| 54 | OC_User::createUser($this->user3, 'pass'); |
||
| 55 | OC_User::createUser($this->user4, 'pass'); |
||
| 56 | OC_User::createUser($this->user5, 'pass'); |
||
| 57 | OC_User::createUser($this->user6, 'pass'); // no group |
||
| 58 | OC_User::createUser($this->groupAndUser, 'pass'); |
||
| 59 | OC_User::setUserId($this->user1); |
||
| 60 | OC_Group::clearBackends(); |
||
| 61 | OC_Group::useBackend(new OC_Group_Dummy); |
||
| 62 | $this->group1 = $this->getUniqueID('group1_'); |
||
| 63 | $this->group2 = $this->getUniqueID('group2_'); |
||
| 64 | OC_Group::createGroup($this->group1); |
||
| 65 | OC_Group::createGroup($this->group2); |
||
| 66 | OC_Group::createGroup($this->groupAndUser); |
||
| 67 | OC_Group::addToGroup($this->user1, $this->group1); |
||
| 68 | OC_Group::addToGroup($this->user2, $this->group1); |
||
| 69 | OC_Group::addToGroup($this->user3, $this->group1); |
||
| 70 | OC_Group::addToGroup($this->user2, $this->group2); |
||
| 71 | OC_Group::addToGroup($this->user4, $this->group2); |
||
| 72 | OC_Group::addToGroup($this->user2, $this->groupAndUser); |
||
| 73 | OC_Group::addToGroup($this->user3, $this->groupAndUser); |
||
| 74 | OCP\Share::registerBackend('test', 'Test_Share_Backend'); |
||
| 75 | OC_Hook::clear('OCP\\Share'); |
||
| 76 | OC::registerShareHooks(); |
||
| 77 | $this->resharing = \OC::$server->getAppConfig()->getValue('core', 'shareapi_allow_resharing', 'yes'); |
||
| 78 | \OC::$server->getAppConfig()->setValue('core', 'shareapi_allow_resharing', 'yes'); |
||
| 79 | |||
| 80 | // 20 Minutes in the past, 20 minutes in the future. |
||
| 81 | $now = time(); |
||
| 82 | $dateFormat = 'Y-m-d H:i:s'; |
||
| 83 | $this->dateInPast = date($dateFormat, $now - 20 * 60); |
||
| 84 | $this->dateInFuture = date($dateFormat, $now + 20 * 60); |
||
| 85 | } |
||
| 86 | |||
| 87 | protected function tearDown() { |
||
| 88 | $query = OC_DB::prepare('DELETE FROM `*PREFIX*share` WHERE `item_type` = ?'); |
||
| 89 | $query->execute(array('test')); |
||
| 90 | \OC::$server->getAppConfig()->setValue('core', 'shareapi_allow_resharing', $this->resharing); |
||
| 91 | |||
| 92 | OC_User::deleteUser($this->user1); |
||
| 93 | OC_User::deleteUser($this->user2); |
||
| 94 | OC_User::deleteUser($this->user3); |
||
| 95 | OC_User::deleteUser($this->user4); |
||
| 96 | OC_User::deleteUser($this->user5); |
||
| 97 | OC_User::deleteUser($this->user6); |
||
| 98 | OC_User::deleteUser($this->groupAndUser); |
||
| 99 | |||
| 100 | OC_Group::deleteGroup($this->group1); |
||
| 101 | OC_Group::deleteGroup($this->group2); |
||
| 102 | OC_Group::deleteGroup($this->groupAndUser); |
||
| 103 | |||
| 104 | $this->logout(); |
||
| 105 | parent::tearDown(); |
||
| 106 | } |
||
| 107 | |||
| 108 | protected function setHttpHelper($httpHelper) { |
||
| 109 | \OC::$server->registerService('HTTPHelper', function () use ($httpHelper) { |
||
| 110 | return $httpHelper; |
||
| 111 | }); |
||
| 112 | } |
||
| 113 | |||
| 114 | public function testShareInvalidShareType() { |
||
| 115 | $message = 'Share type foobar is not valid for test.txt'; |
||
| 116 | try { |
||
| 117 | OCP\Share::shareItem('test', 'test.txt', 'foobar', $this->user2, \OCP\Constants::PERMISSION_READ); |
||
| 118 | } catch (Exception $exception) { |
||
| 119 | $this->assertEquals($message, $exception->getMessage()); |
||
| 120 | } |
||
| 121 | } |
||
| 122 | |||
| 123 | public function testInvalidItemType() { |
||
| 168 | |||
| 169 | protected function shareUserOneTestFileWithUserTwo() { |
||
| 170 | OC_User::setUserId($this->user1); |
||
| 171 | $this->assertTrue( |
||
| 172 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ), |
||
| 173 | 'Failed asserting that user 1 successfully shared text.txt with user 2.' |
||
| 174 | ); |
||
| 175 | $this->assertContains( |
||
| 176 | 'test.txt', |
||
| 177 | OCP\Share::getItemShared('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 178 | 'Failed asserting that test.txt is a shared file of user 1.' |
||
| 179 | ); |
||
| 180 | |||
| 181 | OC_User::setUserId($this->user2); |
||
| 182 | $this->assertContains( |
||
| 183 | 'test.txt', |
||
| 184 | OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 185 | 'Failed asserting that user 2 has access to test.txt after initial sharing.' |
||
| 186 | ); |
||
| 187 | } |
||
| 188 | |||
| 189 | protected function shareUserTestFileAsLink() { |
||
| 190 | OC_User::setUserId($this->user1); |
||
| 191 | $result = OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_LINK, null, \OCP\Constants::PERMISSION_READ); |
||
| 192 | $this->assertTrue(is_string($result)); |
||
| 193 | } |
||
| 194 | |||
| 195 | /** |
||
| 196 | * @param string $sharer |
||
| 197 | * @param string $receiver |
||
| 198 | */ |
||
| 199 | protected function shareUserTestFileWithUser($sharer, $receiver) { |
||
| 200 | OC_User::setUserId($sharer); |
||
| 201 | $this->assertTrue( |
||
| 202 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $receiver, \OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_SHARE), |
||
| 203 | 'Failed asserting that ' . $sharer . ' successfully shared text.txt with ' . $receiver . '.' |
||
| 204 | ); |
||
| 205 | $this->assertContains( |
||
| 206 | 'test.txt', |
||
| 207 | OCP\Share::getItemShared('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 208 | 'Failed asserting that test.txt is a shared file of ' . $sharer . '.' |
||
| 209 | ); |
||
| 210 | |||
| 211 | OC_User::setUserId($receiver); |
||
| 212 | $this->assertContains( |
||
| 213 | 'test.txt', |
||
| 214 | OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 215 | 'Failed asserting that ' . $receiver . ' has access to test.txt after initial sharing.' |
||
| 216 | ); |
||
| 217 | } |
||
| 218 | |||
| 219 | public function testShareWithUser() { |
||
| 220 | // Invalid shares |
||
| 221 | $message = 'Sharing test.txt failed, because you can not share with yourself'; |
||
| 222 | try { |
||
| 223 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user1, \OCP\Constants::PERMISSION_READ); |
||
| 224 | $this->fail('Exception was expected: '.$message); |
||
| 225 | } catch (Exception $exception) { |
||
| 226 | $this->assertEquals($message, $exception->getMessage()); |
||
| 227 | } |
||
| 228 | $message = 'Sharing test.txt failed, because the user foobar does not exist'; |
||
| 229 | try { |
||
| 230 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, 'foobar', \OCP\Constants::PERMISSION_READ); |
||
| 231 | $this->fail('Exception was expected: '.$message); |
||
| 232 | } catch (Exception $exception) { |
||
| 233 | $this->assertEquals($message, $exception->getMessage()); |
||
| 234 | } |
||
| 235 | $message = 'Sharing foobar failed, because the sharing backend for test could not find its source'; |
||
| 236 | try { |
||
| 237 | OCP\Share::shareItem('test', 'foobar', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ); |
||
| 238 | $this->fail('Exception was expected: '.$message); |
||
| 239 | } catch (Exception $exception) { |
||
| 240 | $this->assertEquals($message, $exception->getMessage()); |
||
| 241 | } |
||
| 242 | |||
| 243 | // Valid share |
||
| 244 | $this->shareUserOneTestFileWithUserTwo(); |
||
| 245 | |||
| 246 | // Attempt to share again |
||
| 247 | OC_User::setUserId($this->user1); |
||
| 248 | $message = 'Sharing test.txt failed, because this item is already shared with '.$this->user2; |
||
| 249 | try { |
||
| 250 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ); |
||
| 251 | $this->fail('Exception was expected: '.$message); |
||
| 252 | } catch (Exception $exception) { |
||
| 253 | $this->assertEquals($message, $exception->getMessage()); |
||
| 254 | } |
||
| 255 | |||
| 256 | // Attempt to share back |
||
| 257 | OC_User::setUserId($this->user2); |
||
| 258 | $message = 'Sharing failed, because the user '.$this->user1.' is the original sharer'; |
||
| 259 | try { |
||
| 260 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user1, \OCP\Constants::PERMISSION_READ); |
||
| 261 | $this->fail('Exception was expected: '.$message); |
||
| 262 | } catch (Exception $exception) { |
||
| 263 | $this->assertEquals($message, $exception->getMessage()); |
||
| 264 | } |
||
| 265 | |||
| 266 | // Unshare |
||
| 267 | OC_User::setUserId($this->user1); |
||
| 268 | $this->assertTrue(OCP\Share::unshare('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2)); |
||
| 269 | |||
| 270 | // Attempt reshare without share permission |
||
| 271 | $this->assertTrue(OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ)); |
||
| 272 | OC_User::setUserId($this->user2); |
||
| 273 | $message = 'Sharing test.txt failed, because resharing is not allowed'; |
||
| 274 | try { |
||
| 275 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user3, \OCP\Constants::PERMISSION_READ); |
||
| 276 | $this->fail('Exception was expected: '.$message); |
||
| 277 | } catch (Exception $exception) { |
||
| 278 | $this->assertEquals($message, $exception->getMessage()); |
||
| 279 | } |
||
| 280 | |||
| 281 | // Owner grants share and update permission |
||
| 282 | OC_User::setUserId($this->user1); |
||
| 283 | $this->assertTrue(OCP\Share::setPermissions('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_UPDATE | \OCP\Constants::PERMISSION_SHARE)); |
||
| 284 | |||
| 285 | // Attempt reshare with escalated permissions |
||
| 286 | OC_User::setUserId($this->user2); |
||
| 287 | $message = 'Sharing test.txt failed, because the permissions exceed permissions granted to '.$this->user2; |
||
| 288 | try { |
||
| 289 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user3, \OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_DELETE); |
||
| 290 | $this->fail('Exception was expected: '.$message); |
||
| 291 | } catch (Exception $exception) { |
||
| 292 | $this->assertEquals($message, $exception->getMessage()); |
||
| 293 | } |
||
| 294 | |||
| 295 | // Valid reshare |
||
| 296 | $this->assertTrue(OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user3, \OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_UPDATE)); |
||
| 297 | $this->assertEquals(array('test.txt'), OCP\Share::getItemShared('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE)); |
||
| 298 | OC_User::setUserId($this->user3); |
||
| 299 | $this->assertEquals(array('test.txt'), OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE)); |
||
| 300 | $this->assertEquals(array(\OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_UPDATE), OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_PERMISSIONS)); |
||
| 301 | |||
| 302 | // Attempt to escalate permissions |
||
| 303 | OC_User::setUserId($this->user2); |
||
| 304 | $message = 'Setting permissions for test.txt failed, because the permissions exceed permissions granted to '.$this->user2; |
||
| 305 | try { |
||
| 306 | OCP\Share::setPermissions('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user3, \OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_DELETE); |
||
| 307 | $this->fail('Exception was expected: '.$message); |
||
| 308 | } catch (Exception $exception) { |
||
| 309 | $this->assertEquals($message, $exception->getMessage()); |
||
| 310 | } |
||
| 311 | |||
| 312 | // Remove update permission |
||
| 313 | OC_User::setUserId($this->user1); |
||
| 314 | $this->assertTrue(OCP\Share::setPermissions('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_SHARE)); |
||
| 315 | OC_User::setUserId($this->user2); |
||
| 316 | $this->assertEquals(array(\OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_SHARE), OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_PERMISSIONS)); |
||
| 317 | OC_User::setUserId($this->user3); |
||
| 318 | $this->assertEquals(array(\OCP\Constants::PERMISSION_READ), OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_PERMISSIONS)); |
||
| 319 | |||
| 320 | // Remove share permission |
||
| 321 | OC_User::setUserId($this->user1); |
||
| 322 | $this->assertTrue(OCP\Share::setPermissions('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ)); |
||
| 323 | OC_User::setUserId($this->user2); |
||
| 324 | $this->assertEquals(array(\OCP\Constants::PERMISSION_READ), OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_PERMISSIONS)); |
||
| 325 | OC_User::setUserId($this->user3); |
||
| 326 | $this->assertSame(array(), OCP\Share::getItemSharedWith('test', 'test.txt')); |
||
| 327 | |||
| 328 | // Reshare again, and then have owner unshare |
||
| 329 | OC_User::setUserId($this->user1); |
||
| 330 | $this->assertTrue(OCP\Share::setPermissions('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_SHARE)); |
||
| 331 | OC_User::setUserId($this->user2); |
||
| 332 | $this->assertTrue(OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user3, \OCP\Constants::PERMISSION_READ)); |
||
| 333 | OC_User::setUserId($this->user1); |
||
| 334 | $this->assertTrue(OCP\Share::unshare('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2)); |
||
| 335 | OC_User::setUserId($this->user2); |
||
| 336 | $this->assertSame(array(), OCP\Share::getItemSharedWith('test', 'test.txt')); |
||
| 337 | OC_User::setUserId($this->user3); |
||
| 338 | $this->assertSame(array(), OCP\Share::getItemSharedWith('test', 'test.txt')); |
||
| 339 | |||
| 340 | // Attempt target conflict |
||
| 341 | OC_User::setUserId($this->user1); |
||
| 342 | $this->assertTrue(OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ)); |
||
| 343 | OC_User::setUserId($this->user3); |
||
| 344 | $this->assertTrue(OCP\Share::shareItem('test', 'share.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ)); |
||
| 345 | |||
| 346 | OC_User::setUserId($this->user2); |
||
| 347 | $to_test = OCP\Share::getItemsSharedWith('test', Test_Share_Backend::FORMAT_TARGET); |
||
| 348 | $this->assertEquals(2, count($to_test)); |
||
| 349 | $this->assertTrue(in_array('test.txt', $to_test)); |
||
| 350 | $this->assertTrue(in_array('test1.txt', $to_test)); |
||
| 351 | |||
| 352 | // Unshare from self |
||
| 353 | $this->assertTrue(OCP\Share::unshareFromSelf('test', 'test.txt')); |
||
| 354 | $this->assertEquals(array('test1.txt'), OCP\Share::getItemsSharedWith('test', Test_Share_Backend::FORMAT_TARGET)); |
||
| 355 | |||
| 356 | // Unshare from self via source |
||
| 357 | $this->assertTrue(OCP\Share::unshareFromSelf('test', 'share.txt', true)); |
||
| 358 | $this->assertEquals(array(), OCP\Share::getItemsSharedWith('test', Test_Share_Backend::FORMAT_TARGET)); |
||
| 359 | |||
| 360 | OC_User::setUserId($this->user1); |
||
| 361 | $this->assertTrue(OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ)); |
||
| 362 | OC_User::setUserId($this->user3); |
||
| 363 | $this->assertTrue(OCP\Share::shareItem('test', 'share.txt', OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ)); |
||
| 364 | |||
| 365 | OC_User::setUserId($this->user2); |
||
| 366 | $to_test = OCP\Share::getItemsSharedWith('test', Test_Share_Backend::FORMAT_TARGET); |
||
| 367 | $this->assertEquals(2, count($to_test)); |
||
| 368 | $this->assertTrue(in_array('test.txt', $to_test)); |
||
| 369 | $this->assertTrue(in_array('test1.txt', $to_test)); |
||
| 370 | |||
| 371 | // Remove user |
||
| 372 | OC_User::setUserId($this->user1); |
||
| 373 | OC_User::deleteUser($this->user1); |
||
| 374 | OC_User::setUserId($this->user2); |
||
| 375 | $this->assertEquals(array('test1.txt'), OCP\Share::getItemsSharedWith('test', Test_Share_Backend::FORMAT_TARGET)); |
||
| 376 | } |
||
| 377 | |||
| 378 | public function testShareWithUserExpirationExpired() { |
||
| 379 | OC_User::setUserId($this->user1); |
||
| 380 | $this->shareUserOneTestFileWithUserTwo(); |
||
| 381 | $this->shareUserTestFileAsLink(); |
||
| 382 | |||
| 383 | // manipulate share table and set expire date to the past |
||
| 384 | $query = \OC_DB::prepare('UPDATE `*PREFIX*share` SET `expiration` = ? WHERE `item_type` = ? AND `item_source` = ? AND `uid_owner` = ? AND `share_type` = ?'); |
||
| 385 | $query->bindValue(1, new \DateTime($this->dateInPast), 'datetime'); |
||
| 386 | $query->bindValue(2, 'test'); |
||
| 387 | $query->bindValue(3, 'test.txt'); |
||
| 388 | $query->bindValue(4, $this->user1); |
||
| 389 | $query->bindValue(5, \OCP\Share::SHARE_TYPE_LINK); |
||
| 390 | $query->execute(); |
||
| 391 | |||
| 392 | $shares = OCP\Share::getItemsShared('test'); |
||
| 393 | $this->assertSame(1, count($shares)); |
||
| 394 | $share = reset($shares); |
||
| 395 | $this->assertSame(\OCP\Share::SHARE_TYPE_USER, $share['share_type']); |
||
| 396 | } |
||
| 397 | |||
| 398 | public function testGetShareFromOutsideFilesFolder() { |
||
| 399 | OC_User::setUserId($this->user1); |
||
| 400 | $view = new \OC\Files\View('/' . $this->user1 . '/'); |
||
| 401 | $view->mkdir('files/test'); |
||
| 402 | $view->mkdir('files/test/sub'); |
||
| 403 | |||
| 404 | $view->mkdir('files_trashbin'); |
||
| 405 | $view->mkdir('files_trashbin/files'); |
||
| 406 | |||
| 407 | $fileInfo = $view->getFileInfo('files/test/sub'); |
||
| 408 | $this->assertInstanceOf('\OC\Files\FileInfo', $fileInfo); |
||
| 409 | $fileId = $fileInfo->getId(); |
||
| 410 | |||
| 411 | $this->assertTrue( |
||
| 412 | OCP\Share::shareItem('folder', $fileId, OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ), |
||
| 413 | 'Failed asserting that user 1 successfully shared "test/sub" with user 2.' |
||
| 414 | ); |
||
| 415 | |||
| 416 | $result = OCP\Share::getItemShared('folder', $fileId, Test_Share_Backend::FORMAT_SOURCE); |
||
| 417 | $this->assertNotEmpty($result); |
||
| 418 | |||
| 419 | $result = OCP\Share::getItemSharedWithUser('folder', $fileId, $this->user2); |
||
| 420 | $this->assertNotEmpty($result); |
||
| 421 | |||
| 422 | $result = OCP\Share::getItemsSharedWithUser('folder', $this->user2); |
||
| 423 | $this->assertNotEmpty($result); |
||
| 424 | |||
| 425 | // move to trash (keeps file id) |
||
| 426 | $view->rename('files/test', 'files_trashbin/files/test'); |
||
| 427 | |||
| 428 | $result = OCP\Share::getItemShared('folder', $fileId, Test_Share_Backend::FORMAT_SOURCE); |
||
| 429 | $this->assertEmpty($result, 'Share must not be returned for files outside of "files"'); |
||
| 430 | |||
| 431 | $result = OCP\Share::getItemSharedWithUser('folder', $fileId, $this->user2); |
||
| 432 | $this->assertEmpty($result, 'Share must not be returned for files outside of "files"'); |
||
| 433 | |||
| 434 | $result = OCP\Share::getItemsSharedWithUser('folder', $this->user2); |
||
| 435 | $this->assertEmpty($result, 'Share must not be returned for files outside of "files"'); |
||
| 436 | } |
||
| 437 | |||
| 438 | public function testSetExpireDateInPast() { |
||
| 439 | OC_User::setUserId($this->user1); |
||
| 440 | $this->shareUserOneTestFileWithUserTwo(); |
||
| 441 | $this->shareUserTestFileAsLink(); |
||
| 442 | |||
| 443 | $setExpireDateFailed = false; |
||
| 444 | try { |
||
| 445 | $this->assertTrue( |
||
| 446 | OCP\Share::setExpirationDate('test', 'test.txt', $this->dateInPast, ''), |
||
| 447 | 'Failed asserting that user 1 successfully set an expiration date for the test.txt share.' |
||
| 448 | ); |
||
| 449 | } catch (\Exception $e) { |
||
| 450 | $setExpireDateFailed = true; |
||
| 451 | } |
||
| 452 | |||
| 453 | $this->assertTrue($setExpireDateFailed); |
||
| 454 | } |
||
| 455 | |||
| 456 | public function testShareWithUserExpirationValid() { |
||
| 457 | OC_User::setUserId($this->user1); |
||
| 458 | $this->shareUserOneTestFileWithUserTwo(); |
||
| 459 | $this->shareUserTestFileAsLink(); |
||
| 460 | |||
| 461 | |||
| 462 | $this->assertTrue( |
||
| 463 | OCP\Share::setExpirationDate('test', 'test.txt', $this->dateInFuture, ''), |
||
| 464 | 'Failed asserting that user 1 successfully set an expiration date for the test.txt share.' |
||
| 465 | ); |
||
| 466 | |||
| 467 | $shares = OCP\Share::getItemsShared('test'); |
||
| 468 | $this->assertSame(2, count($shares)); |
||
| 469 | |||
| 470 | } |
||
| 471 | |||
| 472 | /* |
||
| 473 | * if user is in a group excluded from resharing, then the share permission should |
||
| 474 | * be removed |
||
| 475 | */ |
||
| 476 | public function testShareWithUserAndUserIsExcludedFromResharing() { |
||
| 477 | |||
| 478 | OC_User::setUserId($this->user1); |
||
| 479 | $this->assertTrue( |
||
| 480 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_USER, $this->user4, \OCP\Constants::PERMISSION_ALL), |
||
| 481 | 'Failed asserting that user 1 successfully shared text.txt with user 4.' |
||
| 482 | ); |
||
| 483 | $this->assertContains( |
||
| 484 | 'test.txt', |
||
| 485 | OCP\Share::getItemShared('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 486 | 'Failed asserting that test.txt is a shared file of user 1.' |
||
| 487 | ); |
||
| 488 | |||
| 489 | // exclude group2 from sharing |
||
| 490 | \OC::$server->getAppConfig()->setValue('core', 'shareapi_exclude_groups_list', $this->group2); |
||
| 491 | \OC::$server->getAppConfig()->setValue('core', 'shareapi_exclude_groups', "yes"); |
||
| 492 | |||
| 493 | OC_User::setUserId($this->user4); |
||
| 494 | |||
| 495 | $share = OCP\Share::getItemSharedWith('test', 'test.txt'); |
||
| 496 | |||
| 497 | $this->assertSame(\OCP\Constants::PERMISSION_ALL & ~\OCP\Constants::PERMISSION_SHARE, $share['permissions'], |
||
| 498 | 'Failed asserting that user 4 is excluded from re-sharing'); |
||
| 499 | |||
| 500 | \OC::$server->getAppConfig()->deleteKey('core', 'shareapi_exclude_groups_list'); |
||
| 501 | \OC::$server->getAppConfig()->deleteKey('core', 'shareapi_exclude_groups'); |
||
| 502 | |||
| 503 | } |
||
| 504 | |||
| 505 | public function testSharingAFolderThatIsSharedWithAGroupOfTheOwner() { |
||
| 506 | OC_User::setUserId($this->user1); |
||
| 507 | $view = new \OC\Files\View('/' . $this->user1 . '/'); |
||
| 508 | $view->mkdir('files/test'); |
||
| 509 | $view->mkdir('files/test/sub1'); |
||
| 510 | $view->mkdir('files/test/sub1/sub2'); |
||
| 511 | |||
| 512 | $fileInfo = $view->getFileInfo('files/test/sub1'); |
||
| 513 | $this->assertInstanceOf('\OC\Files\FileInfo', $fileInfo); |
||
| 514 | $fileId = $fileInfo->getId(); |
||
| 515 | |||
| 516 | $this->assertTrue( |
||
| 517 | OCP\Share::shareItem('folder', $fileId, OCP\Share::SHARE_TYPE_GROUP, $this->group1, \OCP\Constants::PERMISSION_READ + \OCP\Constants::PERMISSION_CREATE), |
||
| 518 | 'Failed asserting that user 1 successfully shared "test/sub1" with group 1.' |
||
| 519 | ); |
||
| 520 | |||
| 521 | $result = OCP\Share::getItemShared('folder', $fileId, Test_Share_Backend::FORMAT_SOURCE); |
||
| 522 | $this->assertNotEmpty($result); |
||
| 523 | $this->assertEquals(\OCP\Constants::PERMISSION_READ + \OCP\Constants::PERMISSION_CREATE, $result['permissions']); |
||
| 524 | |||
| 525 | $fileInfo = $view->getFileInfo('files/test/sub1/sub2'); |
||
| 526 | $this->assertInstanceOf('\OC\Files\FileInfo', $fileInfo); |
||
| 527 | $fileId = $fileInfo->getId(); |
||
| 528 | |||
| 529 | $this->assertTrue( |
||
| 530 | OCP\Share::shareItem('folder', $fileId, OCP\Share::SHARE_TYPE_USER, $this->user4, \OCP\Constants::PERMISSION_READ), |
||
| 531 | 'Failed asserting that user 1 successfully shared "test/sub1/sub2" with user 4.' |
||
| 532 | ); |
||
| 533 | |||
| 534 | $result = OCP\Share::getItemShared('folder', $fileId, Test_Share_Backend::FORMAT_SOURCE); |
||
| 535 | $this->assertNotEmpty($result); |
||
| 536 | $this->assertEquals(\OCP\Constants::PERMISSION_READ, $result['permissions']); |
||
| 537 | } |
||
| 538 | |||
| 539 | public function testSharingAFileInsideAFolderThatIsAlreadyShared() { |
||
| 540 | OC_User::setUserId($this->user1); |
||
| 541 | $view = new \OC\Files\View('/' . $this->user1 . '/'); |
||
| 542 | $view->mkdir('files/test'); |
||
| 543 | $view->mkdir('files/test/sub1'); |
||
| 544 | $view->file_put_contents('files/test/sub1/file.txt', 'abc'); |
||
| 545 | |||
| 546 | $folderInfo = $view->getFileInfo('files/test/sub1'); |
||
| 547 | $this->assertInstanceOf('\OC\Files\FileInfo', $folderInfo); |
||
| 548 | $folderId = $folderInfo->getId(); |
||
| 549 | |||
| 550 | $fileInfo = $view->getFileInfo('files/test/sub1/file.txt'); |
||
| 551 | $this->assertInstanceOf('\OC\Files\FileInfo', $fileInfo); |
||
| 552 | $fileId = $fileInfo->getId(); |
||
| 553 | |||
| 554 | $this->assertTrue( |
||
| 555 | OCP\Share::shareItem('folder', $folderId, OCP\Share::SHARE_TYPE_GROUP, $this->group2, \OCP\Constants::PERMISSION_READ + \OCP\Constants::PERMISSION_UPDATE), |
||
| 556 | 'Failed asserting that user 1 successfully shared "test/sub1" with group 2.' |
||
| 557 | ); |
||
| 558 | |||
| 559 | $this->assertTrue( |
||
| 560 | OCP\Share::shareItem('file', $fileId, OCP\Share::SHARE_TYPE_USER, $this->user2, \OCP\Constants::PERMISSION_READ), |
||
| 561 | 'Failed asserting that user 1 successfully shared "test/sub1/file.txt" with user 2.' |
||
| 562 | ); |
||
| 563 | |||
| 564 | $result = \OCP\Share::getItemsSharedWithUser('file', $this->user2); |
||
| 565 | $this->assertCount(2, $result); |
||
| 566 | |||
| 567 | foreach ($result as $share) { |
||
| 568 | $itemName = substr($share['path'], strrpos($share['path'], '/')); |
||
| 569 | $this->assertSame($itemName, $share['file_target'], 'Asserting that the file_target is the last segment of the path'); |
||
| 570 | $this->assertSame($share['item_target'], '/' . $share['item_source'], 'Asserting that the item is the item that was shared'); |
||
| 571 | } |
||
| 572 | } |
||
| 573 | |||
| 574 | protected function shareUserOneTestFileWithGroupOne() { |
||
| 575 | OC_User::setUserId($this->user1); |
||
| 576 | $this->assertTrue( |
||
| 577 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_GROUP, $this->group1, \OCP\Constants::PERMISSION_READ), |
||
| 578 | 'Failed asserting that user 1 successfully shared text.txt with group 1.' |
||
| 579 | ); |
||
| 580 | $this->assertContains( |
||
| 581 | 'test.txt', |
||
| 582 | OCP\Share::getItemShared('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 583 | 'Failed asserting that test.txt is a shared file of user 1.' |
||
| 584 | ); |
||
| 585 | |||
| 586 | OC_User::setUserId($this->user2); |
||
| 587 | $this->assertContains( |
||
| 588 | 'test.txt', |
||
| 589 | OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 590 | 'Failed asserting that user 2 has access to test.txt after initial sharing.' |
||
| 591 | ); |
||
| 592 | |||
| 593 | OC_User::setUserId($this->user3); |
||
| 594 | $this->assertContains( |
||
| 595 | 'test.txt', |
||
| 596 | OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 597 | 'Failed asserting that user 3 has access to test.txt after initial sharing.' |
||
| 598 | ); |
||
| 599 | } |
||
| 600 | |||
| 601 | public function testShareWithGroup() { |
||
| 756 | |||
| 757 | /** |
||
| 758 | * Test that unsharing from group will also delete all |
||
| 759 | * child entries |
||
| 760 | */ |
||
| 761 | public function testShareWithGroupThenUnshare() { |
||
| 762 | OC_User::setUserId($this->user5); |
||
| 763 | OCP\Share::shareItem( |
||
| 764 | 'test', |
||
| 765 | 'test.txt', |
||
| 766 | OCP\Share::SHARE_TYPE_GROUP, |
||
| 767 | $this->group1, |
||
| 768 | \OCP\Constants::PERMISSION_ALL |
||
| 769 | ); |
||
| 770 | |||
| 771 | $targetUsers = array($this->user1, $this->user2, $this->user3); |
||
| 772 | |||
| 773 | View Code Duplication | foreach($targetUsers as $targetUser) { |
|
| 774 | OC_User::setUserId($targetUser); |
||
| 775 | $items = OCP\Share::getItemsSharedWithUser( |
||
| 776 | 'test', |
||
| 777 | $targetUser, |
||
| 778 | Test_Share_Backend::FORMAT_TARGET |
||
| 779 | ); |
||
| 780 | $this->assertEquals(1, count($items)); |
||
| 781 | } |
||
| 782 | |||
| 783 | OC_User::setUserId($this->user5); |
||
| 784 | OCP\Share::unshare( |
||
| 785 | 'test', |
||
| 786 | 'test.txt', |
||
| 787 | OCP\Share::SHARE_TYPE_GROUP, |
||
| 788 | $this->group1 |
||
| 789 | ); |
||
| 790 | |||
| 791 | // verify that all were deleted |
||
| 792 | View Code Duplication | foreach($targetUsers as $targetUser) { |
|
| 793 | OC_User::setUserId($targetUser); |
||
| 794 | $items = OCP\Share::getItemsSharedWithUser( |
||
| 795 | 'test', |
||
| 796 | $targetUser, |
||
| 797 | Test_Share_Backend::FORMAT_TARGET |
||
| 798 | ); |
||
| 799 | $this->assertEquals(0, count($items)); |
||
| 800 | } |
||
| 801 | } |
||
| 802 | |||
| 803 | public function testShareWithGroupAndUserBothHaveTheSameId() { |
||
| 804 | |||
| 805 | $this->shareUserTestFileWithUser($this->user1, $this->groupAndUser); |
||
| 806 | |||
| 807 | OC_User::setUserId($this->groupAndUser); |
||
| 808 | |||
| 809 | $this->assertEquals(array('test.txt'), OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 810 | '"groupAndUser"-User does not see the file but it was shared with him'); |
||
| 811 | |||
| 812 | OC_User::setUserId($this->user2); |
||
| 813 | $this->assertEquals(array(), OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 814 | 'User2 sees test.txt but it was only shared with the user "groupAndUser" and not with group'); |
||
| 815 | |||
| 816 | OC_User::setUserId($this->user1); |
||
| 817 | $this->assertTrue(OCP\Share::unshareAll('test', 'test.txt')); |
||
| 818 | |||
| 819 | $this->assertTrue( |
||
| 820 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_GROUP, $this->groupAndUser, \OCP\Constants::PERMISSION_READ), |
||
| 821 | 'Failed asserting that user 1 successfully shared text.txt with group 1.' |
||
| 822 | ); |
||
| 823 | |||
| 824 | OC_User::setUserId($this->groupAndUser); |
||
| 825 | $this->assertEquals(array(), OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 826 | '"groupAndUser"-User sees test.txt but it was only shared with the group "groupAndUser" and not with the user'); |
||
| 827 | |||
| 828 | OC_User::setUserId($this->user2); |
||
| 829 | $this->assertEquals(array('test.txt'), OCP\Share::getItemSharedWith('test', 'test.txt', Test_Share_Backend::FORMAT_SOURCE), |
||
| 830 | 'User2 does not see test.txt but it was shared with the group "groupAndUser"'); |
||
| 831 | |||
| 832 | OC_User::setUserId($this->user1); |
||
| 833 | $this->assertTrue(OCP\Share::unshareAll('test', 'test.txt')); |
||
| 834 | |||
| 835 | } |
||
| 836 | |||
| 837 | /** |
||
| 838 | * @param boolean|string $token |
||
| 839 | * @return array |
||
| 840 | */ |
||
| 841 | protected function getShareByValidToken($token) { |
||
| 842 | $row = OCP\Share::getShareByToken($token); |
||
| 843 | $this->assertInternalType( |
||
| 844 | 'array', |
||
| 845 | $row, |
||
| 846 | "Failed asserting that a share for token $token exists." |
||
| 847 | ); |
||
| 848 | return $row; |
||
| 849 | } |
||
| 850 | |||
| 851 | public function testGetItemSharedWithUser() { |
||
| 852 | OC_User::setUserId($this->user1); |
||
| 853 | |||
| 854 | //add dummy values to the share table |
||
| 855 | $query = \OC_DB::prepare('INSERT INTO `*PREFIX*share` (' |
||
| 856 | .' `item_type`, `item_source`, `item_target`, `share_type`,' |
||
| 857 | .' `share_with`, `uid_owner`) VALUES (?,?,?,?,?,?)'); |
||
| 858 | $args = array('test', 99, 'target1', OCP\Share::SHARE_TYPE_USER, $this->user2, $this->user1); |
||
| 859 | $query->execute($args); |
||
| 860 | $args = array('test', 99, 'target2', OCP\Share::SHARE_TYPE_USER, $this->user4, $this->user1); |
||
| 861 | $query->execute($args); |
||
| 862 | $args = array('test', 99, 'target3', OCP\Share::SHARE_TYPE_USER, $this->user3, $this->user2); |
||
| 863 | $query->execute($args); |
||
| 864 | $args = array('test', 99, 'target4', OCP\Share::SHARE_TYPE_USER, $this->user3, $this->user4); |
||
| 865 | $query->execute($args); |
||
| 866 | $args = array('test', 99, 'target4', OCP\Share::SHARE_TYPE_USER, $this->user6, $this->user4); |
||
| 867 | $query->execute($args); |
||
| 868 | |||
| 869 | |||
| 870 | $result1 = \OCP\Share::getItemSharedWithUser('test', 99, $this->user2, $this->user1); |
||
| 871 | $this->assertSame(1, count($result1)); |
||
| 872 | $this->verifyResult($result1, array('target1')); |
||
| 873 | |||
| 874 | $result2 = \OCP\Share::getItemSharedWithUser('test', 99, null, $this->user1); |
||
| 875 | $this->assertSame(2, count($result2)); |
||
| 876 | $this->verifyResult($result2, array('target1', 'target2')); |
||
| 877 | |||
| 878 | $result3 = \OCP\Share::getItemSharedWithUser('test', 99, $this->user3); |
||
| 879 | $this->assertSame(2, count($result3)); |
||
| 880 | $this->verifyResult($result3, array('target3', 'target4')); |
||
| 881 | |||
| 882 | $result4 = \OCP\Share::getItemSharedWithUser('test', 99, null, null); |
||
| 883 | $this->assertSame(5, count($result4)); // 5 because target4 appears twice |
||
| 884 | $this->verifyResult($result4, array('target1', 'target2', 'target3', 'target4')); |
||
| 885 | |||
| 886 | $result6 = \OCP\Share::getItemSharedWithUser('test', 99, $this->user6, null); |
||
| 887 | $this->assertSame(1, count($result6)); |
||
| 888 | $this->verifyResult($result6, array('target4')); |
||
| 889 | } |
||
| 890 | |||
| 891 | public function testGetItemSharedWithUserFromGroupShare() { |
||
| 892 | OC_User::setUserId($this->user1); |
||
| 893 | |||
| 894 | //add dummy values to the share table |
||
| 895 | $query = \OC_DB::prepare('INSERT INTO `*PREFIX*share` (' |
||
| 896 | .' `item_type`, `item_source`, `item_target`, `share_type`,' |
||
| 897 | .' `share_with`, `uid_owner`) VALUES (?,?,?,?,?,?)'); |
||
| 898 | $args = array('test', 99, 'target1', OCP\Share::SHARE_TYPE_GROUP, $this->group1, $this->user1); |
||
| 899 | $query->execute($args); |
||
| 900 | $args = array('test', 99, 'target2', OCP\Share::SHARE_TYPE_GROUP, $this->group2, $this->user1); |
||
| 901 | $query->execute($args); |
||
| 902 | $args = array('test', 99, 'target3', OCP\Share::SHARE_TYPE_GROUP, $this->group1, $this->user2); |
||
| 903 | $query->execute($args); |
||
| 904 | $args = array('test', 99, 'target4', OCP\Share::SHARE_TYPE_GROUP, $this->group1, $this->user4); |
||
| 905 | $query->execute($args); |
||
| 906 | |||
| 907 | // user2 is in group1 and group2 |
||
| 908 | $result1 = \OCP\Share::getItemSharedWithUser('test', 99, $this->user2, $this->user1); |
||
| 909 | $this->assertSame(2, count($result1)); |
||
| 910 | $this->verifyResult($result1, array('target1', 'target2')); |
||
| 911 | |||
| 912 | $result2 = \OCP\Share::getItemSharedWithUser('test', 99, null, $this->user1); |
||
| 913 | $this->assertSame(2, count($result2)); |
||
| 914 | $this->verifyResult($result2, array('target1', 'target2')); |
||
| 915 | |||
| 916 | // user3 is in group1 and group2 |
||
| 917 | $result3 = \OCP\Share::getItemSharedWithUser('test', 99, $this->user3); |
||
| 918 | $this->assertSame(3, count($result3)); |
||
| 919 | $this->verifyResult($result3, array('target1', 'target3', 'target4')); |
||
| 920 | |||
| 921 | $result4 = \OCP\Share::getItemSharedWithUser('test', 99, null, null); |
||
| 922 | $this->assertSame(4, count($result4)); |
||
| 923 | $this->verifyResult($result4, array('target1', 'target2', 'target3', 'target4')); |
||
| 924 | |||
| 925 | $result6 = \OCP\Share::getItemSharedWithUser('test', 99, $this->user6, null); |
||
| 926 | $this->assertSame(0, count($result6)); |
||
| 927 | } |
||
| 928 | |||
| 929 | public function verifyResult($result, $expected) { |
||
| 930 | foreach ($result as $r) { |
||
| 931 | if (in_array($r['item_target'], $expected)) { |
||
| 932 | $key = array_search($r['item_target'], $expected); |
||
| 933 | unset($expected[$key]); |
||
| 934 | } |
||
| 935 | } |
||
| 936 | $this->assertEmpty($expected, 'did not found all expected values'); |
||
| 937 | } |
||
| 938 | |||
| 939 | public function testGetShareSubItemsWhenUserNotInGroup() { |
||
| 940 | OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_GROUP, $this->group1, \OCP\Constants::PERMISSION_READ); |
||
| 941 | |||
| 942 | $result = \OCP\Share::getItemsSharedWithUser('test', $this->user2); |
||
| 943 | $this->assertCount(1, $result); |
||
| 944 | |||
| 945 | $groupShareId = array_keys($result)[0]; |
||
| 946 | |||
| 947 | // remove user from group |
||
| 948 | $userObject = \OC::$server->getUserManager()->get($this->user2); |
||
| 949 | \OC::$server->getGroupManager()->get($this->group1)->removeUser($userObject); |
||
| 950 | |||
| 951 | $result = \OCP\Share::getItemsSharedWithUser('test', $this->user2); |
||
| 952 | $this->assertCount(0, $result); |
||
| 953 | |||
| 954 | // test with buggy data |
||
| 955 | $qb = \OC::$server->getDatabaseConnection()->getQueryBuilder(); |
||
| 956 | $qb->insert('share') |
||
| 957 | ->values([ |
||
| 958 | 'share_type' => $qb->expr()->literal(2), // group sub-share |
||
| 959 | 'share_with' => $qb->expr()->literal($this->user2), |
||
| 960 | 'parent' => $qb->expr()->literal($groupShareId), |
||
| 961 | 'uid_owner' => $qb->expr()->literal($this->user1), |
||
| 962 | 'item_type' => $qb->expr()->literal('test'), |
||
| 963 | 'item_source' => $qb->expr()->literal('test.txt'), |
||
| 964 | 'item_target' => $qb->expr()->literal('test.txt'), |
||
| 965 | 'file_target' => $qb->expr()->literal('test2.txt'), |
||
| 966 | 'permissions' => $qb->expr()->literal(1), |
||
| 967 | 'stime' => $qb->expr()->literal(time()), |
||
| 968 | ])->execute(); |
||
| 969 | |||
| 970 | $result = \OCP\Share::getItemsSharedWithUser('test', $this->user2); |
||
| 971 | $this->assertCount(0, $result); |
||
| 972 | |||
| 973 | $qb->delete('share')->execute(); |
||
| 974 | } |
||
| 975 | |||
| 976 | public function testShareItemWithLink() { |
||
| 977 | OC_User::setUserId($this->user1); |
||
| 978 | $token = OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_LINK, null, \OCP\Constants::PERMISSION_READ); |
||
| 979 | $this->assertInternalType( |
||
| 980 | 'string', |
||
| 981 | $token, |
||
| 982 | 'Failed asserting that user 1 successfully shared text.txt as link with token.' |
||
| 983 | ); |
||
| 984 | |||
| 985 | // testGetShareByTokenNoExpiration |
||
| 986 | $row = $this->getShareByValidToken($token); |
||
| 987 | $this->assertEmpty( |
||
| 988 | $row['expiration'], |
||
| 989 | 'Failed asserting that the returned row does not have an expiration date.' |
||
| 990 | ); |
||
| 991 | |||
| 992 | // testGetShareByTokenExpirationValid |
||
| 993 | $this->assertTrue( |
||
| 994 | OCP\Share::setExpirationDate('test', 'test.txt', $this->dateInFuture, ''), |
||
| 995 | 'Failed asserting that user 1 successfully set a future expiration date for the test.txt share.' |
||
| 996 | ); |
||
| 997 | $row = $this->getShareByValidToken($token); |
||
| 998 | $this->assertNotEmpty( |
||
| 999 | $row['expiration'], |
||
| 1000 | 'Failed asserting that the returned row has an expiration date.' |
||
| 1001 | ); |
||
| 1002 | |||
| 1003 | // manipulate share table and set expire date to the past |
||
| 1004 | $query = \OC_DB::prepare('UPDATE `*PREFIX*share` SET `expiration` = ? WHERE `item_type` = ? AND `item_source` = ? AND `uid_owner` = ? AND `share_type` = ?'); |
||
| 1005 | $query->bindValue(1, new \DateTime($this->dateInPast), 'datetime'); |
||
| 1006 | $query->bindValue(2, 'test'); |
||
| 1007 | $query->bindValue(3, 'test.txt'); |
||
| 1008 | $query->bindValue(4, $this->user1); |
||
| 1009 | $query->bindValue(5, \OCP\Share::SHARE_TYPE_LINK); |
||
| 1010 | $query->execute(); |
||
| 1011 | |||
| 1012 | $this->assertFalse( |
||
| 1013 | OCP\Share::getShareByToken($token), |
||
| 1014 | 'Failed asserting that an expired share could not be found.' |
||
| 1015 | ); |
||
| 1016 | } |
||
| 1017 | |||
| 1018 | public function testShareItemWithLinkAndDefaultExpireDate() { |
||
| 1019 | OC_User::setUserId($this->user1); |
||
| 1020 | |||
| 1021 | $config = \OC::$server->getConfig(); |
||
| 1022 | |||
| 1023 | $config->setAppValue('core', 'shareapi_default_expire_date', 'yes'); |
||
| 1024 | $config->setAppValue('core', 'shareapi_expire_after_n_days', '2'); |
||
| 1025 | |||
| 1026 | $token = OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_LINK, null, \OCP\Constants::PERMISSION_READ); |
||
| 1027 | $this->assertInternalType( |
||
| 1028 | 'string', |
||
| 1029 | $token, |
||
| 1030 | 'Failed asserting that user 1 successfully shared text.txt as link with token.' |
||
| 1031 | ); |
||
| 1032 | |||
| 1033 | // share should have default expire date |
||
| 1034 | |||
| 1035 | $row = $this->getShareByValidToken($token); |
||
| 1036 | $this->assertNotEmpty( |
||
| 1037 | $row['expiration'], |
||
| 1038 | 'Failed asserting that the returned row has an default expiration date.' |
||
| 1039 | ); |
||
| 1040 | |||
| 1041 | $config->deleteAppValue('core', 'shareapi_default_expire_date'); |
||
| 1042 | $config->deleteAppValue('core', 'shareapi_expire_after_n_days'); |
||
| 1043 | |||
| 1044 | } |
||
| 1045 | |||
| 1046 | View Code Duplication | public function dataShareWithRemoteUserAndRemoteIsInvalid() { |
|
| 1047 | return [ |
||
| 1048 | // Invalid path |
||
| 1049 | array('user@'), |
||
| 1050 | |||
| 1051 | // Invalid user |
||
| 1052 | array('@server'), |
||
| 1053 | array('us/er@server'), |
||
| 1054 | array('us:er@server'), |
||
| 1055 | |||
| 1056 | // Invalid splitting |
||
| 1057 | array('user'), |
||
| 1058 | array(''), |
||
| 1059 | array('us/erserver'), |
||
| 1060 | array('us:erserver'), |
||
| 1061 | ]; |
||
| 1062 | } |
||
| 1063 | |||
| 1064 | /** |
||
| 1065 | * @dataProvider dataShareWithRemoteUserAndRemoteIsInvalid |
||
| 1066 | * |
||
| 1067 | * @param string $remoteId |
||
| 1068 | * @expectedException \OC\HintException |
||
| 1069 | */ |
||
| 1070 | public function testShareWithRemoteUserAndRemoteIsInvalid($remoteId) { |
||
| 1074 | |||
| 1075 | public function testUnshareAll() { |
||
| 1076 | $this->shareUserTestFileWithUser($this->user1, $this->user2); |
||
| 1077 | $this->shareUserTestFileWithUser($this->user2, $this->user3); |
||
| 1078 | $this->shareUserTestFileWithUser($this->user3, $this->user4); |
||
| 1079 | $this->shareUserOneTestFileWithGroupOne(); |
||
| 1080 | |||
| 1081 | OC_User::setUserId($this->user1); |
||
| 1082 | $this->assertEquals( |
||
| 1083 | array('test.txt', 'test.txt'), |
||
| 1084 | OCP\Share::getItemsShared('test', Test_Share_Backend::FORMAT_SOURCE), |
||
| 1085 | 'Failed asserting that the test.txt file is shared exactly two times by user1.' |
||
| 1086 | ); |
||
| 1087 | |||
| 1088 | OC_User::setUserId($this->user2); |
||
| 1089 | $this->assertEquals( |
||
| 1090 | array('test.txt'), |
||
| 1091 | OCP\Share::getItemsShared('test', Test_Share_Backend::FORMAT_SOURCE), |
||
| 1092 | 'Failed asserting that the test.txt file is shared exactly once by user2.' |
||
| 1093 | ); |
||
| 1094 | |||
| 1095 | OC_User::setUserId($this->user3); |
||
| 1096 | $this->assertEquals( |
||
| 1097 | array('test.txt'), |
||
| 1098 | OCP\Share::getItemsShared('test', Test_Share_Backend::FORMAT_SOURCE), |
||
| 1099 | 'Failed asserting that the test.txt file is shared exactly once by user3.' |
||
| 1100 | ); |
||
| 1101 | |||
| 1102 | $this->assertTrue( |
||
| 1103 | OCP\Share::unshareAll('test', 'test.txt'), |
||
| 1104 | 'Failed asserting that user 3 successfully unshared all shares of the test.txt share.' |
||
| 1105 | ); |
||
| 1106 | |||
| 1107 | $this->assertEquals( |
||
| 1108 | array(), |
||
| 1109 | OCP\Share::getItemsShared('test'), |
||
| 1110 | 'Failed asserting that the share of the test.txt file by user 3 has been removed.' |
||
| 1111 | ); |
||
| 1112 | |||
| 1113 | OC_User::setUserId($this->user1); |
||
| 1114 | $this->assertEquals( |
||
| 1115 | array(), |
||
| 1116 | OCP\Share::getItemsShared('test'), |
||
| 1117 | 'Failed asserting that both shares of the test.txt file by user 1 have been removed.' |
||
| 1118 | ); |
||
| 1119 | |||
| 1120 | OC_User::setUserId($this->user2); |
||
| 1121 | $this->assertEquals( |
||
| 1122 | array(), |
||
| 1123 | OCP\Share::getItemsShared('test'), |
||
| 1124 | 'Failed asserting that the share of the test.txt file by user 2 has been removed.' |
||
| 1125 | ); |
||
| 1126 | } |
||
| 1127 | |||
| 1128 | /** |
||
| 1129 | * @dataProvider checkPasswordProtectedShareDataProvider |
||
| 1130 | * @param $expected |
||
| 1131 | * @param $item |
||
| 1132 | */ |
||
| 1133 | public function testCheckPasswordProtectedShare($expected, $item) { |
||
| 1134 | \OC::$server->getSession()->set('public_link_authenticated', 100); |
||
| 1135 | $result = \OCP\Share::checkPasswordProtectedShare($item); |
||
| 1136 | $this->assertEquals($expected, $result); |
||
| 1137 | } |
||
| 1138 | |||
| 1139 | function checkPasswordProtectedShareDataProvider() { |
||
| 1140 | return array( |
||
| 1141 | array(true, array()), |
||
| 1142 | array(true, array('share_with' => null)), |
||
| 1143 | array(true, array('share_with' => '')), |
||
| 1144 | array(true, array('share_with' => '1234567890', 'share_type' => '1')), |
||
| 1145 | array(true, array('share_with' => '1234567890', 'share_type' => 1)), |
||
| 1146 | array(true, array('share_with' => '1234567890', 'share_type' => '3', 'id' => 100)), |
||
| 1147 | array(true, array('share_with' => '1234567890', 'share_type' => 3, 'id' => 100)), |
||
| 1148 | array(false, array('share_with' => '1234567890', 'share_type' => '3', 'id' => 101)), |
||
| 1149 | array(false, array('share_with' => '1234567890', 'share_type' => 3, 'id' => 101)), |
||
| 1150 | ); |
||
| 1151 | } |
||
| 1152 | |||
| 1153 | /** |
||
| 1154 | * @dataProvider urls |
||
| 1155 | */ |
||
| 1156 | function testRemoveProtocolFromUrl($url, $expectedResult) { |
||
| 1157 | $share = new \OC\Share\Share(); |
||
| 1158 | $result = self::invokePrivate($share, 'removeProtocolFromUrl', array($url)); |
||
| 1159 | $this->assertSame($expectedResult, $result); |
||
| 1160 | } |
||
| 1161 | |||
| 1162 | function urls() { |
||
| 1163 | return array( |
||
| 1164 | array('http://owncloud.org', 'owncloud.org'), |
||
| 1165 | array('https://owncloud.org', 'owncloud.org'), |
||
| 1166 | array('owncloud.org', 'owncloud.org'), |
||
| 1167 | ); |
||
| 1168 | } |
||
| 1169 | |||
| 1170 | public function dataRemoteShareUrlCalls() { |
||
| 1171 | return [ |
||
| 1172 | ['admin@localhost', 'localhost'], |
||
| 1173 | ['admin@https://localhost', 'localhost'], |
||
| 1174 | ['admin@http://localhost', 'localhost'], |
||
| 1175 | ['admin@localhost/subFolder', 'localhost/subFolder'], |
||
| 1176 | ]; |
||
| 1177 | } |
||
| 1178 | |||
| 1179 | /** |
||
| 1180 | * @dataProvider dataRemoteShareUrlCalls |
||
| 1181 | * |
||
| 1182 | * @param string $shareWith |
||
| 1183 | * @param string $urlHost |
||
| 1184 | */ |
||
| 1185 | public function testRemoteShareUrlCalls($shareWith, $urlHost) { |
||
| 1186 | $oldHttpHelper = \OC::$server->query('HTTPHelper'); |
||
| 1187 | $httpHelperMock = $this->getMockBuilder('OC\HttpHelper') |
||
| 1188 | ->disableOriginalConstructor() |
||
| 1189 | ->getMock(); |
||
| 1190 | $this->setHttpHelper($httpHelperMock); |
||
| 1191 | |||
| 1192 | $httpHelperMock->expects($this->at(0)) |
||
| 1193 | ->method('post') |
||
| 1194 | ->with($this->stringStartsWith('https://' . $urlHost . '/ocs/v1.php/cloud/shares'), $this->anything()) |
||
| 1195 | ->willReturn(['success' => false, 'result' => 'Exception']); |
||
| 1196 | $httpHelperMock->expects($this->at(1)) |
||
| 1197 | ->method('post') |
||
| 1198 | ->with($this->stringStartsWith('http://' . $urlHost . '/ocs/v1.php/cloud/shares'), $this->anything()) |
||
| 1199 | ->willReturn(['success' => true, 'result' => json_encode(['ocs' => ['meta' => ['statuscode' => 100]]])]); |
||
| 1200 | |||
| 1201 | \OCP\Share::shareItem('test', 'test.txt', \OCP\Share::SHARE_TYPE_REMOTE, $shareWith, \OCP\Constants::PERMISSION_READ); |
||
| 1202 | $shares = \OCP\Share::getItemShared('test', 'test.txt'); |
||
| 1203 | $share = array_shift($shares); |
||
| 1204 | |||
| 1205 | $httpHelperMock->expects($this->at(0)) |
||
| 1206 | ->method('post') |
||
| 1207 | ->with($this->stringStartsWith('https://' . $urlHost . '/ocs/v1.php/cloud/shares/' . $share['id'] . '/unshare'), $this->anything()) |
||
| 1208 | ->willReturn(['success' => false, 'result' => 'Exception']); |
||
| 1209 | $httpHelperMock->expects($this->at(1)) |
||
| 1210 | ->method('post') |
||
| 1211 | ->with($this->stringStartsWith('http://' . $urlHost . '/ocs/v1.php/cloud/shares/' . $share['id'] . '/unshare'), $this->anything()) |
||
| 1212 | ->willReturn(['success' => true, 'result' => json_encode(['ocs' => ['meta' => ['statuscode' => 100]]])]); |
||
| 1213 | |||
| 1214 | \OCP\Share::unshare('test', 'test.txt', \OCP\Share::SHARE_TYPE_REMOTE, $shareWith); |
||
| 1215 | $this->setHttpHelper($oldHttpHelper); |
||
| 1216 | } |
||
| 1217 | |||
| 1218 | /** |
||
| 1219 | * @dataProvider dataProviderTestGroupItems |
||
| 1220 | * @param array $ungrouped |
||
| 1221 | * @param array $grouped |
||
| 1222 | */ |
||
| 1223 | function testGroupItems($ungrouped, $grouped) { |
||
| 1224 | |||
| 1225 | $result = DummyShareClass::groupItemsTest($ungrouped); |
||
| 1226 | |||
| 1227 | $this->compareArrays($grouped, $result); |
||
| 1228 | |||
| 1229 | } |
||
| 1230 | |||
| 1231 | function compareArrays($result, $expectedResult) { |
||
| 1232 | foreach ($expectedResult as $key => $value) { |
||
| 1233 | if (is_array($value)) { |
||
| 1234 | $this->compareArrays($result[$key], $value); |
||
| 1235 | } else { |
||
| 1236 | $this->assertSame($value, $result[$key]); |
||
| 1237 | } |
||
| 1238 | } |
||
| 1239 | } |
||
| 1240 | |||
| 1241 | function dataProviderTestGroupItems() { |
||
| 1242 | return array( |
||
| 1243 | // one array with one share |
||
| 1244 | array( |
||
| 1245 | array( // input |
||
| 1246 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_ALL, 'item_target' => 't1')), |
||
| 1247 | array( // expected result |
||
| 1248 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_ALL, 'item_target' => 't1'))), |
||
| 1249 | // two shares both point to the same source |
||
| 1250 | array( |
||
| 1251 | array( // input |
||
| 1252 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_READ, 'item_target' => 't1'), |
||
| 1253 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_UPDATE, 'item_target' => 't1'), |
||
| 1254 | ), |
||
| 1255 | array( // expected result |
||
| 1256 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_UPDATE, 'item_target' => 't1', |
||
| 1257 | 'grouped' => array( |
||
| 1258 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_READ, 'item_target' => 't1'), |
||
| 1259 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_UPDATE, 'item_target' => 't1'), |
||
| 1260 | ) |
||
| 1261 | ), |
||
| 1262 | ) |
||
| 1263 | ), |
||
| 1264 | // two shares both point to the same source but with different targets |
||
| 1265 | array( |
||
| 1266 | array( // input |
||
| 1267 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_READ, 'item_target' => 't1'), |
||
| 1268 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_UPDATE, 'item_target' => 't2'), |
||
| 1269 | ), |
||
| 1270 | array( // expected result |
||
| 1271 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_READ, 'item_target' => 't1'), |
||
| 1272 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_UPDATE, 'item_target' => 't2'), |
||
| 1273 | ) |
||
| 1274 | ), |
||
| 1275 | // three shares two point to the same source |
||
| 1276 | array( |
||
| 1277 | array( // input |
||
| 1278 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_READ, 'item_target' => 't1'), |
||
| 1279 | array('item_source' => 2, 'permissions' => \OCP\Constants::PERMISSION_CREATE, 'item_target' => 't2'), |
||
| 1280 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_UPDATE, 'item_target' => 't1'), |
||
| 1281 | ), |
||
| 1282 | array( // expected result |
||
| 1283 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_READ | \OCP\Constants::PERMISSION_UPDATE, 'item_target' => 't1', |
||
| 1284 | 'grouped' => array( |
||
| 1285 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_READ, 'item_target' => 't1'), |
||
| 1286 | array('item_source' => 1, 'permissions' => \OCP\Constants::PERMISSION_UPDATE, 'item_target' => 't1'), |
||
| 1287 | ) |
||
| 1288 | ), |
||
| 1289 | array('item_source' => 2, 'permissions' => \OCP\Constants::PERMISSION_CREATE, 'item_target' => 't2'), |
||
| 1290 | ) |
||
| 1291 | ), |
||
| 1292 | ); |
||
| 1293 | } |
||
| 1294 | |||
| 1295 | /** |
||
| 1296 | * Ensure that we do not allow removing a an expiration date from a link share if this |
||
| 1297 | * is enforced by the settings. |
||
| 1298 | */ |
||
| 1299 | public function testClearExpireDateWhileEnforced() { |
||
| 1300 | OC_User::setUserId($this->user1); |
||
| 1301 | |||
| 1302 | \OC::$server->getAppConfig()->setValue('core', 'shareapi_default_expire_date', 'yes'); |
||
| 1303 | \OC::$server->getAppConfig()->setValue('core', 'shareapi_expire_after_n_days', '2'); |
||
| 1304 | \OC::$server->getAppConfig()->setValue('core', 'shareapi_enforce_expire_date', 'yes'); |
||
| 1305 | |||
| 1306 | $token = OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_LINK, null, \OCP\Constants::PERMISSION_READ); |
||
| 1307 | $this->assertInternalType( |
||
| 1308 | 'string', |
||
| 1309 | $token, |
||
| 1310 | 'Failed asserting that user 1 successfully shared text.txt as link with token.' |
||
| 1311 | ); |
||
| 1312 | |||
| 1313 | $setExpireDateFailed = false; |
||
| 1314 | try { |
||
| 1315 | $this->assertTrue( |
||
| 1316 | OCP\Share::setExpirationDate('test', 'test.txt', '', ''), |
||
| 1317 | 'Failed asserting that user 1 successfully set an expiration date for the test.txt share.' |
||
| 1318 | ); |
||
| 1319 | } catch (\Exception $e) { |
||
| 1320 | $setExpireDateFailed = true; |
||
| 1321 | } |
||
| 1322 | |||
| 1323 | $this->assertTrue($setExpireDateFailed); |
||
| 1324 | |||
| 1325 | \OC::$server->getAppConfig()->deleteKey('core', 'shareapi_default_expire_date'); |
||
| 1326 | \OC::$server->getAppConfig()->deleteKey('core', 'shareapi_expire_after_n_days'); |
||
| 1327 | \OC::$server->getAppConfig()->deleteKey('core', 'shareapi_enforce_expire_date'); |
||
| 1328 | } |
||
| 1329 | |||
| 1330 | /** |
||
| 1331 | * Cannot set password is there is no user |
||
| 1332 | * |
||
| 1333 | * @expectedException Exception |
||
| 1334 | * @expectedExceptionMessage User not logged in |
||
| 1335 | */ |
||
| 1336 | public function testSetPasswordNoUser() { |
||
| 1337 | $userSession = $this->getMockBuilder('\OCP\IUserSession') |
||
| 1338 | ->disableOriginalConstructor() |
||
| 1339 | ->getMock(); |
||
| 1340 | |||
| 1341 | $connection = $this->getMockBuilder('\OC\DB\Connection') |
||
| 1342 | ->disableOriginalConstructor() |
||
| 1343 | ->getMock(); |
||
| 1344 | |||
| 1345 | $config = $this->getMockBuilder('\OCP\IConfig') |
||
| 1346 | ->disableOriginalConstructor() |
||
| 1347 | ->getMock(); |
||
| 1348 | |||
| 1349 | \OC\Share\Share::setPassword($userSession, $connection, $config, 1, 'pass'); |
||
| 1350 | } |
||
| 1351 | |||
| 1352 | public function testPasswords() { |
||
| 1353 | $pass = 'secret'; |
||
| 1354 | |||
| 1355 | $this->shareUserTestFileAsLink(); |
||
| 1356 | |||
| 1357 | $userSession = \OC::$server->getUserSession(); |
||
| 1358 | $connection = \OC::$server->getDatabaseConnection(); |
||
| 1359 | $config = $this->getMockBuilder('\OCP\IConfig') |
||
| 1360 | ->disableOriginalConstructor() |
||
| 1361 | ->getMock(); |
||
| 1362 | |||
| 1363 | // Find the share ID in the db |
||
| 1364 | $qb = $connection->getQueryBuilder(); |
||
| 1365 | $qb->select('id') |
||
| 1366 | ->from('share') |
||
| 1367 | ->where($qb->expr()->eq('item_type', $qb->createParameter('type'))) |
||
| 1368 | ->andWhere($qb->expr()->eq('item_source', $qb->createParameter('source'))) |
||
| 1369 | ->andWhere($qb->expr()->eq('uid_owner', $qb->createParameter('owner'))) |
||
| 1370 | ->andWhere($qb->expr()->eq('share_type', $qb->createParameter('share_type'))) |
||
| 1371 | ->setParameter('type', 'test') |
||
| 1372 | ->setParameter('source', 'test.txt') |
||
| 1373 | ->setParameter('owner', $this->user1) |
||
| 1374 | ->setParameter('share_type', \OCP\Share::SHARE_TYPE_LINK); |
||
| 1375 | |||
| 1376 | $res = $qb->execute()->fetchAll(); |
||
| 1377 | $this->assertCount(1, $res); |
||
| 1378 | $id = $res[0]['id']; |
||
| 1379 | |||
| 1380 | // Set password on share |
||
| 1381 | $res = \OC\Share\Share::setPassword($userSession, $connection, $config, $id, $pass); |
||
| 1382 | $this->assertTrue($res); |
||
| 1383 | |||
| 1384 | // Fetch the hash from the database |
||
| 1385 | $qb = $connection->getQueryBuilder(); |
||
| 1386 | $qb->select('share_with') |
||
| 1387 | ->from('share') |
||
| 1388 | ->where($qb->expr()->eq('id', $qb->createParameter('id'))) |
||
| 1389 | ->setParameter('id', $id); |
||
| 1390 | $hash = $qb->execute()->fetch()['share_with']; |
||
| 1391 | |||
| 1392 | $hasher = \OC::$server->getHasher(); |
||
| 1393 | |||
| 1394 | // Verify hash |
||
| 1395 | $this->assertTrue($hasher->verify($pass, $hash)); |
||
| 1396 | } |
||
| 1397 | |||
| 1398 | /** |
||
| 1399 | * Test setting a password when everything is fine |
||
| 1400 | */ |
||
| 1401 | public function testSetPassword() { |
||
| 1449 | |||
| 1450 | /** |
||
| 1451 | * @expectedException Exception |
||
| 1452 | * @expectedExceptionMessage Cannot remove password |
||
| 1453 | * |
||
| 1454 | * Test removing a password when password is enforced |
||
| 1455 | */ |
||
| 1456 | public function testSetPasswordRemove() { |
||
| 1457 | $user = $this->getMockBuilder('\OCP\IUser') |
||
| 1458 | ->disableOriginalConstructor() |
||
| 1459 | ->getMock(); |
||
| 1460 | $user->method('getUID')->willReturn('user'); |
||
| 1461 | |||
| 1462 | $userSession = $this->getMockBuilder('\OCP\IUserSession') |
||
| 1463 | ->disableOriginalConstructor() |
||
| 1464 | ->getMock(); |
||
| 1465 | $userSession->method('getUser')->willReturn($user); |
||
| 1466 | |||
| 1467 | |||
| 1468 | $ex = $this->getMockBuilder('\OC\DB\QueryBuilder\ExpressionBuilder') |
||
| 1469 | ->disableOriginalConstructor() |
||
| 1470 | ->getMock(); |
||
| 1471 | $qb = $this->getMockBuilder('\OC\DB\QueryBuilder\QueryBuilder') |
||
| 1472 | ->disableOriginalConstructor() |
||
| 1473 | ->getMock(); |
||
| 1474 | $qb->method('update')->will($this->returnSelf()); |
||
| 1475 | $qb->method('select')->will($this->returnSelf()); |
||
| 1476 | $qb->method('from')->will($this->returnSelf()); |
||
| 1477 | $qb->method('set')->will($this->returnSelf()); |
||
| 1478 | $qb->method('where')->will($this->returnSelf()); |
||
| 1479 | $qb->method('andWhere')->will($this->returnSelf()); |
||
| 1480 | $qb->method('setParameter')->will($this->returnSelf()); |
||
| 1481 | $qb->method('expr')->willReturn($ex); |
||
| 1482 | |||
| 1483 | $ret = $this->getMockBuilder('\Doctrine\DBAL\Driver\ResultStatement') |
||
| 1484 | ->disableOriginalConstructor() |
||
| 1485 | ->getMock(); |
||
| 1486 | $ret->method('fetch')->willReturn(['uid_owner' => 'user']); |
||
| 1487 | $qb->method('execute')->willReturn($ret); |
||
| 1488 | |||
| 1489 | |||
| 1490 | $connection = $this->getMockBuilder('\OC\DB\Connection') |
||
| 1491 | ->disableOriginalConstructor() |
||
| 1492 | ->getMock(); |
||
| 1493 | $connection->method('getQueryBuilder')->willReturn($qb); |
||
| 1494 | |||
| 1495 | $config = $this->getMockBuilder('\OCP\IConfig') |
||
| 1496 | ->disableOriginalConstructor() |
||
| 1497 | ->getMock(); |
||
| 1498 | $config->method('getAppValue')->willReturn('yes'); |
||
| 1499 | |||
| 1500 | \OC\Share\Share::setPassword($userSession, $connection, $config, 1, ''); |
||
| 1501 | } |
||
| 1502 | |||
| 1503 | /** |
||
| 1504 | * @expectedException Exception |
||
| 1505 | * @expectedExceptionMessage Share not found |
||
| 1506 | * |
||
| 1507 | * Test modification of invaid share |
||
| 1508 | */ |
||
| 1509 | View Code Duplication | public function testSetPasswordInvalidShare() { |
|
| 1510 | $user = $this->getMockBuilder('\OCP\IUser') |
||
| 1511 | ->disableOriginalConstructor() |
||
| 1512 | ->getMock(); |
||
| 1513 | $user->method('getUID')->willReturn('user'); |
||
| 1514 | |||
| 1515 | $userSession = $this->getMockBuilder('\OCP\IUserSession') |
||
| 1516 | ->disableOriginalConstructor() |
||
| 1517 | ->getMock(); |
||
| 1518 | $userSession->method('getUser')->willReturn($user); |
||
| 1519 | |||
| 1520 | |||
| 1521 | $ex = $this->getMockBuilder('\OC\DB\QueryBuilder\ExpressionBuilder') |
||
| 1522 | ->disableOriginalConstructor() |
||
| 1523 | ->getMock(); |
||
| 1524 | $qb = $this->getMockBuilder('\OC\DB\QueryBuilder\QueryBuilder') |
||
| 1525 | ->disableOriginalConstructor() |
||
| 1526 | ->getMock(); |
||
| 1527 | $qb->method('update')->will($this->returnSelf()); |
||
| 1528 | $qb->method('set')->will($this->returnSelf()); |
||
| 1529 | $qb->method('where')->will($this->returnSelf()); |
||
| 1530 | $qb->method('andWhere')->will($this->returnSelf()); |
||
| 1531 | $qb->method('select')->will($this->returnSelf()); |
||
| 1532 | $qb->method('from')->will($this->returnSelf()); |
||
| 1533 | $qb->method('setParameter')->will($this->returnSelf()); |
||
| 1534 | $qb->method('expr')->willReturn($ex); |
||
| 1535 | |||
| 1536 | $ret = $this->getMockBuilder('\Doctrine\DBAL\Driver\ResultStatement') |
||
| 1537 | ->disableOriginalConstructor() |
||
| 1538 | ->getMock(); |
||
| 1539 | $ret->method('fetch')->willReturn([]); |
||
| 1540 | $qb->method('execute')->willReturn($ret); |
||
| 1541 | |||
| 1542 | |||
| 1543 | $connection = $this->getMockBuilder('\OC\DB\Connection') |
||
| 1544 | ->disableOriginalConstructor() |
||
| 1545 | ->getMock(); |
||
| 1546 | $connection->method('getQueryBuilder')->willReturn($qb); |
||
| 1547 | |||
| 1548 | $config = $this->getMockBuilder('\OCP\IConfig') |
||
| 1549 | ->disableOriginalConstructor() |
||
| 1550 | ->getMock(); |
||
| 1551 | |||
| 1552 | |||
| 1553 | \OC\Share\Share::setPassword($userSession, $connection, $config, 1, 'pass'); |
||
| 1554 | } |
||
| 1555 | |||
| 1556 | /** |
||
| 1557 | * @expectedException Exception |
||
| 1558 | * @expectedExceptionMessage Cannot update share of a different user |
||
| 1559 | * |
||
| 1560 | * Test modification of share of another user |
||
| 1561 | */ |
||
| 1562 | View Code Duplication | public function testSetPasswordShareOtherUser() { |
|
| 1563 | $user = $this->getMockBuilder('\OCP\IUser') |
||
| 1564 | ->disableOriginalConstructor() |
||
| 1565 | ->getMock(); |
||
| 1566 | $user->method('getUID')->willReturn('user'); |
||
| 1567 | |||
| 1568 | $userSession = $this->getMockBuilder('\OCP\IUserSession') |
||
| 1569 | ->disableOriginalConstructor() |
||
| 1570 | ->getMock(); |
||
| 1571 | $userSession->method('getUser')->willReturn($user); |
||
| 1572 | |||
| 1573 | |||
| 1574 | $ex = $this->getMockBuilder('\OC\DB\QueryBuilder\ExpressionBuilder') |
||
| 1575 | ->disableOriginalConstructor() |
||
| 1576 | ->getMock(); |
||
| 1577 | $qb = $this->getMockBuilder('\OC\DB\QueryBuilder\QueryBuilder') |
||
| 1578 | ->disableOriginalConstructor() |
||
| 1579 | ->getMock(); |
||
| 1580 | $qb->method('update')->will($this->returnSelf()); |
||
| 1581 | $qb->method('set')->will($this->returnSelf()); |
||
| 1582 | $qb->method('where')->will($this->returnSelf()); |
||
| 1583 | $qb->method('andWhere')->will($this->returnSelf()); |
||
| 1584 | $qb->method('select')->will($this->returnSelf()); |
||
| 1585 | $qb->method('from')->will($this->returnSelf()); |
||
| 1586 | $qb->method('setParameter')->will($this->returnSelf()); |
||
| 1587 | $qb->method('expr')->willReturn($ex); |
||
| 1588 | |||
| 1589 | $ret = $this->getMockBuilder('\Doctrine\DBAL\Driver\ResultStatement') |
||
| 1590 | ->disableOriginalConstructor() |
||
| 1591 | ->getMock(); |
||
| 1592 | $ret->method('fetch')->willReturn(['uid_owner' => 'user2']); |
||
| 1593 | $qb->method('execute')->willReturn($ret); |
||
| 1594 | |||
| 1595 | |||
| 1596 | $connection = $this->getMockBuilder('\OC\DB\Connection') |
||
| 1597 | ->disableOriginalConstructor() |
||
| 1598 | ->getMock(); |
||
| 1599 | $connection->method('getQueryBuilder')->willReturn($qb); |
||
| 1600 | |||
| 1601 | $config = $this->getMockBuilder('\OCP\IConfig') |
||
| 1602 | ->disableOriginalConstructor() |
||
| 1603 | ->getMock(); |
||
| 1604 | |||
| 1605 | |||
| 1606 | \OC\Share\Share::setPassword($userSession, $connection, $config, 1, 'pass'); |
||
| 1607 | } |
||
| 1608 | |||
| 1609 | /** |
||
| 1610 | * Make sure that a user cannot have multiple identical shares to remote users |
||
| 1611 | */ |
||
| 1612 | public function testOnlyOneRemoteShare() { |
||
| 1613 | $oldHttpHelper = \OC::$server->query('HTTPHelper'); |
||
| 1614 | $httpHelperMock = $this->getMockBuilder('OC\HttpHelper') |
||
| 1615 | ->disableOriginalConstructor() |
||
| 1616 | ->getMock(); |
||
| 1617 | $this->setHttpHelper($httpHelperMock); |
||
| 1618 | |||
| 1619 | $httpHelperMock->expects($this->at(0)) |
||
| 1620 | ->method('post') |
||
| 1621 | ->with($this->stringStartsWith('https://localhost/ocs/v1.php/cloud/shares'), $this->anything()) |
||
| 1622 | ->willReturn(['success' => true, 'result' => json_encode(['ocs' => ['meta' => ['statuscode' => 100]]])]); |
||
| 1623 | |||
| 1624 | \OCP\Share::shareItem('test', 'test.txt', \OCP\Share::SHARE_TYPE_REMOTE, 'foo@localhost', \OCP\Constants::PERMISSION_READ); |
||
| 1625 | $shares = \OCP\Share::getItemShared('test', 'test.txt'); |
||
| 1626 | $share = array_shift($shares); |
||
| 1627 | |||
| 1628 | //Try share again |
||
| 1629 | try { |
||
| 1630 | \OCP\Share::shareItem('test', 'test.txt', \OCP\Share::SHARE_TYPE_REMOTE, 'foo@localhost', \OCP\Constants::PERMISSION_READ); |
||
| 1631 | $this->fail('Identical remote shares are not allowed'); |
||
| 1632 | } catch (\Exception $e) { |
||
| 1633 | $this->assertEquals('Sharing test.txt failed, because this item is already shared with foo@localhost', $e->getMessage()); |
||
| 1634 | } |
||
| 1635 | |||
| 1636 | $httpHelperMock->expects($this->at(0)) |
||
| 1637 | ->method('post') |
||
| 1638 | ->with($this->stringStartsWith('https://localhost/ocs/v1.php/cloud/shares/' . $share['id'] . '/unshare'), $this->anything()) |
||
| 1639 | ->willReturn(['success' => true, 'result' => json_encode(['ocs' => ['meta' => ['statuscode' => 100]]])]); |
||
| 1640 | |||
| 1641 | \OCP\Share::unshare('test', 'test.txt', \OCP\Share::SHARE_TYPE_REMOTE, 'foo@localhost'); |
||
| 1642 | $this->setHttpHelper($oldHttpHelper); |
||
| 1643 | } |
||
| 1644 | |||
| 1645 | /** |
||
| 1646 | * Test case for #19119 |
||
| 1647 | */ |
||
| 1648 | public function testReshareWithLinkDefaultExpirationDate() { |
||
| 1649 | $config = \OC::$server->getConfig(); |
||
| 1650 | $config->setAppValue('core', 'shareapi_default_expire_date', 'yes'); |
||
| 1651 | $config->setAppValue('core', 'shareapi_expire_after_n_days', '2'); |
||
| 1652 | |||
| 1653 | // Expiration date |
||
| 1654 | $expireAt = time() + 2 * 24*60*60; |
||
| 1655 | $date = new DateTime(); |
||
| 1656 | $date->setTimestamp($expireAt); |
||
| 1657 | $date->setTime(0, 0, 0); |
||
| 1658 | |||
| 1659 | //Share a file from user 1 to user 2 |
||
| 1660 | $this->shareUserTestFileWithUser($this->user1, $this->user2); |
||
| 1661 | |||
| 1662 | //User 2 shares as link |
||
| 1663 | OC_User::setUserId($this->user2); |
||
| 1664 | $result = OCP\Share::shareItem('test', 'test.txt', OCP\Share::SHARE_TYPE_LINK, null, \OCP\Constants::PERMISSION_READ); |
||
| 1665 | $this->assertTrue(is_string($result)); |
||
| 1666 | |||
| 1667 | //Check if expire date is correct |
||
| 1668 | $result = OCP\Share::getItemShared('test', 'test.txt'); |
||
| 1669 | $this->assertCount(1, $result); |
||
| 1670 | $result = reset($result); |
||
| 1671 | $this->assertNotEmpty($result['expiration']); |
||
| 1672 | $expireDate = new DateTime($result['expiration']); |
||
| 1673 | $this->assertEquals($date, $expireDate); |
||
| 1674 | |||
| 1675 | //Unshare |
||
| 1676 | $this->assertTrue(OCP\Share::unshareAll('test', 'test.txt')); |
||
| 1677 | |||
| 1678 | //Reset config |
||
| 1679 | $config->deleteAppValue('core', 'shareapi_default_expire_date'); |
||
| 1680 | $config->deleteAppValue('core', 'shareapi_expire_after_n_days'); |
||
| 1681 | } |
||
| 1682 | |||
| 1683 | public function testShareWithSelfError() { |
||
| 1684 | OC_User::setUserId($this->user1); |
||
| 1685 | $view = new \OC\Files\View('/' . $this->user1 . '/'); |
||
| 1686 | $view->mkdir('files/folder1'); |
||
| 1687 | |||
| 1688 | $fileInfo = $view->getFileInfo('files/folder1'); |
||
| 1689 | $this->assertInstanceOf('\OC\Files\FileInfo', $fileInfo); |
||
| 1690 | $fileId = $fileInfo->getId(); |
||
| 1691 | |||
| 1692 | try { |
||
| 1693 | OCP\Share::shareItem('folder', $fileId, OCP\Share::SHARE_TYPE_USER, $this->user1, \OCP\Constants::PERMISSION_ALL); |
||
| 1694 | $this->fail(); |
||
| 1695 | } catch (\Exception $e) { |
||
| 1696 | $this->assertEquals('Sharing /folder1 failed, because you can not share with yourself', $e->getMessage()); |
||
| 1697 | } |
||
| 1698 | } |
||
| 1699 | |||
| 1700 | public function testShareWithOwnerError() { |
||
| 1722 | } |
||
| 1723 | |||
| 1724 | class DummyShareClass extends \OC\Share\Share { |
||
| 1725 | public static function groupItemsTest($items) { |
||
| 1726 | return parent::groupItems($items, 'test'); |
||
| 1727 | } |
||
| 1728 | } |
||
| 1729 | |||
| 1730 | class DummyHookListener { |
||
| 1731 | static $shareType = null; |
||
| 1732 | |||
| 1733 | public static function listen($params) { |
||
| 1734 | self::$shareType = $params['shareType']; |
||
| 1735 | } |
||
| 1736 | } |
||
| 1737 |
This check looks for access to properties that are not accessible from the current context.
If you need to make a property accessible to another context you can either raise its visibility level or provide an accessible getter in the defining class.