diff --git a/apps/files_external/lib/Config/ConfigAdapter.php b/apps/files_external/lib/Config/ConfigAdapter.php index 8d9c7ea8d1..c9586635ba 100644 --- a/apps/files_external/lib/Config/ConfigAdapter.php +++ b/apps/files_external/lib/Config/ConfigAdapter.php @@ -76,7 +76,7 @@ class ConfigAdapter implements IMountProvider { */ private function prepareStorageConfig(StorageConfig &$storage, IUser $user) { foreach ($storage->getBackendOptions() as $option => $value) { - $storage->setBackendOption($option, \OC_Mount_Config::substitutePlaceholdersInConfig($value)); + $storage->setBackendOption($option, \OC_Mount_Config::substitutePlaceholdersInConfig($value, $user->getUID())); } $objectStore = $storage->getBackendOption('objectstore'); diff --git a/apps/files_external/lib/Config/SimpleSubstitutionTrait.php b/apps/files_external/lib/Config/SimpleSubstitutionTrait.php index 05bd529f1c..1dc5f16779 100644 --- a/apps/files_external/lib/Config/SimpleSubstitutionTrait.php +++ b/apps/files_external/lib/Config/SimpleSubstitutionTrait.php @@ -34,7 +34,7 @@ trait SimpleSubstitutionTrait { * @var string the placeholder without $ prefix * @since 16.0.0 */ - private $placeholder; + protected $placeholder; /** @var string */ protected $sanitizedPlaceholder; diff --git a/apps/files_external/lib/Config/UserContext.php b/apps/files_external/lib/Config/UserContext.php new file mode 100644 index 0000000000..12621d22f5 --- /dev/null +++ b/apps/files_external/lib/Config/UserContext.php @@ -0,0 +1,89 @@ + + * + * @author Julius Härtl + * + * @license GNU AGPL version 3 or any later version + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as + * published by the Free Software Foundation, either version 3 of the + * License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see . + * + */ + +namespace OCA\Files_External\Config; + +use OCP\IRequest; +use OCP\IUser; +use OCP\IUserManager; +use OCP\IUserSession; +use OCP\Share\Exceptions\ShareNotFound; +use OCP\Share\IManager as ShareManager; + +class UserContext { + + /** @var IUserSession */ + private $session; + + /** @var ShareManager */ + private $shareManager; + + /** @var IRequest */ + private $request; + + /** @var string */ + private $userId; + + /** @var IUserManager */ + private $userManager; + + public function __construct(IUserSession $session, ShareManager $manager, IRequest $request, IUserManager $userManager) { + $this->session = $session; + $this->shareManager = $manager; + $this->request = $request; + $this->userManager = $userManager; + } + + public function getSession(): IUserSession { + return $this->session; + } + + public function setUserId(string $userId): void { + $this->userId = $userId; + } + + protected function getUserId(): ?string { + if ($this->userId !== null) { + return $this->userId; + } + if($this->session && $this->session->getUser() !== null) { + return $this->session->getUser()->getUID(); + } + try { + $shareToken = $this->request->getParam('token'); + $share = $this->shareManager->getShareByToken($shareToken); + return $share->getShareOwner(); + } catch (ShareNotFound $e) {} + + return null; + } + + protected function getUser(): ?IUser { + $userId = $this->getUserId(); + if($userId !== null) { + return $this->userManager->get($userId); + } + return null; + } + +} diff --git a/apps/files_external/lib/Config/UserPlaceholderHandler.php b/apps/files_external/lib/Config/UserPlaceholderHandler.php index 721d3bbe02..e442f84a5d 100644 --- a/apps/files_external/lib/Config/UserPlaceholderHandler.php +++ b/apps/files_external/lib/Config/UserPlaceholderHandler.php @@ -23,31 +23,20 @@ namespace OCA\Files_External\Config; -use OCP\IUserSession; - -class UserPlaceholderHandler implements IConfigHandler { +class UserPlaceholderHandler extends UserContext implements IConfigHandler { use SimpleSubstitutionTrait; - /** @var IUserSession */ - private $session; - - public function __construct(IUserSession $session) { - $this->session = $session; - $this->placeholder = 'user'; - } - /** * @param mixed $optionValue * @return mixed the same type as $optionValue * @since 16.0.0 */ public function handle($optionValue) { - $user = $this->session->getUser(); - if($user === null) { + $this->placeholder = 'user'; + $uid = $this->getUserId(); + if($uid === null) { return $optionValue; } - $uid = $user->getUID(); - return $this->processInput($optionValue, $uid); } } diff --git a/apps/files_external/lib/config.php b/apps/files_external/lib/config.php index cc417a837f..85bbbeb57d 100644 --- a/apps/files_external/lib/config.php +++ b/apps/files_external/lib/config.php @@ -50,6 +50,7 @@ use OCA\Files_External\Service\UserGlobalStoragesService; use OCP\IUserManager; use OCA\Files_External\Service\GlobalStoragesService; use OCA\Files_External\Service\UserStoragesService; +use OCA\Files_External\Config\UserContext; /** * Class to configure mount.json globally and for users @@ -107,7 +108,7 @@ class OC_Mount_Config { $mountPoint = '/'.$uid.'/files'.$storage->getMountPoint(); $mountEntry = self::prepareMountPointEntry($storage, false); foreach ($mountEntry['options'] as &$option) { - $option = self::substitutePlaceholdersInConfig($option); + $option = self::substitutePlaceholdersInConfig($option, $uid); } $mountPoints[$mountPoint] = $mountEntry; } @@ -116,7 +117,7 @@ class OC_Mount_Config { $mountPoint = '/'.$uid.'/files'.$storage->getMountPoint(); $mountEntry = self::prepareMountPointEntry($storage, true); foreach ($mountEntry['options'] as &$option) { - $option = self::substitutePlaceholdersInConfig($uid, $option); + $option = self::substitutePlaceholdersInConfig($option, $uid); } $mountPoints[$mountPoint] = $mountEntry; } @@ -211,16 +212,20 @@ class OC_Mount_Config { /** * @param mixed $input + * @param string|null $userId * @return mixed * @throws \OCP\AppFramework\QueryException * @since 16.0.0 */ - public static function substitutePlaceholdersInConfig($input) { + public static function substitutePlaceholdersInConfig($input, string $userId = null) { /** @var BackendService $backendService */ $backendService = self::$app->getContainer()->query(BackendService::class); /** @var IConfigHandler[] $handlers */ $handlers = $backendService->getConfigHandlers(); foreach ($handlers as $handler) { + if ($handler instanceof UserContext && $userId !== null) { + $handler->setUserId($userId); + } $input = $handler->handle($input); } return $input; diff --git a/apps/files_external/tests/Config/UserPlaceholderHandlerTest.php b/apps/files_external/tests/Config/UserPlaceholderHandlerTest.php index b6103c20b4..dcafdd84e3 100644 --- a/apps/files_external/tests/Config/UserPlaceholderHandlerTest.php +++ b/apps/files_external/tests/Config/UserPlaceholderHandlerTest.php @@ -24,8 +24,12 @@ namespace OCA\files_external\tests\Config; use OCA\Files_External\Config\UserPlaceholderHandler; +use OCP\IRequest; use OCP\IUser; +use OCP\IUserManager; use OCP\IUserSession; +use OCP\Share\Exceptions\ShareNotFound; +use OCP\Share\IManager; class UserPlaceholderHandlerTest extends \Test\TestCase { /** @var IUser|\PHPUnit_Framework_MockObject_MockObject */ @@ -34,6 +38,15 @@ class UserPlaceholderHandlerTest extends \Test\TestCase { /** @var IUserSession|\PHPUnit_Framework_MockObject_MockObject */ protected $session; + /** @var IManager|\PHPUnit_Framework_MockObject_MockObject */ + private $shareManager; + + /** @var IRequest|\PHPUnit_Framework_MockObject_MockObject */ + private $request; + + /** @var IUserManager|\PHPUnit_Framework_MockObject_MockObject */ + private $userManager; + /** @var UserPlaceholderHandler */ protected $handler; @@ -45,8 +58,11 @@ class UserPlaceholderHandlerTest extends \Test\TestCase { ->method('getUid') ->willReturn('alice'); $this->session = $this->createMock(IUserSession::class); + $this->shareManager = $this->createMock(IManager::class); + $this->request = $this->createMock(IRequest::class); + $this->userManager = $this->createMock(IUserManager::class); - $this->handler = new UserPlaceholderHandler($this->session); + $this->handler = new UserPlaceholderHandler($this->session, $this->shareManager, $this->request, $this->userManager); } protected function setUser() { @@ -75,6 +91,9 @@ class UserPlaceholderHandlerTest extends \Test\TestCase { * @dataProvider optionProvider */ public function testHandleNoUser($option) { + $this->shareManager->expects($this->once()) + ->method('getShareByToken') + ->willThrowException(new ShareNotFound()); $this->assertSame($option, $this->handler->handle($option)); } diff --git a/apps/user_ldap/lib/Handler/ExtStorageConfigHandler.php b/apps/user_ldap/lib/Handler/ExtStorageConfigHandler.php index 98a3cc7126..ac807a63d1 100644 --- a/apps/user_ldap/lib/Handler/ExtStorageConfigHandler.php +++ b/apps/user_ldap/lib/Handler/ExtStorageConfigHandler.php @@ -25,20 +25,12 @@ namespace OCA\User_LDAP\Handler; use OCA\Files_External\Config\IConfigHandler; use OCA\Files_External\Config\SimpleSubstitutionTrait; +use OCA\Files_External\Config\UserContext; use OCA\User_LDAP\User_Proxy; -use OCP\IUserSession; -class ExtStorageConfigHandler implements IConfigHandler { +class ExtStorageConfigHandler extends UserContext implements IConfigHandler { use SimpleSubstitutionTrait; - /** @var IUserSession */ - private $session; - - public function __construct(IUserSession $session) { - $this->placeholder = 'home'; - $this->session = $session; - } - /** * @param mixed $optionValue * @return mixed the same type as $optionValue @@ -46,7 +38,9 @@ class ExtStorageConfigHandler implements IConfigHandler { * @throws \Exception */ public function handle($optionValue) { - $user = $this->session->getUser(); + $this->placeholder = 'home'; + $user = $this->getUser(); + if($user === null) { return $optionValue; }