Skip to content

Commit 650fe7c

Browse files
committed
fix(Wopi): fall back to super share if share token is not available
On internal shares the controller is called without the share token. But necessary information, like share attributes, might be necessary to know and are available from the super share of the SharedStorage in that case. For this approach was used elsewhere, too, some repetitive code was consolidated in the Helper class. Signed-off-by: Arthur Schiwon <blizzz@arthur-schiwon.de>
1 parent 566baa2 commit 650fe7c

5 files changed

Lines changed: 57 additions & 47 deletions

File tree

lib/Controller/AssetsController.php

Lines changed: 13 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,9 @@
66

77
namespace OCA\Richdocuments\Controller;
88

9-
use OCA\Files_Sharing\SharedStorage;
109
use OCA\Richdocuments\Controller\Attribute\RestrictToWopiServer;
1110
use OCA\Richdocuments\Db\AssetMapper;
11+
use OCA\Richdocuments\Helper;
1212
use OCA\Richdocuments\Service\UserScopeService;
1313
use OCP\AppFramework\Controller;
1414
use OCP\AppFramework\Db\DoesNotExistException;
@@ -30,20 +30,25 @@ class AssetsController extends Controller {
3030
private UserScopeService $userScopeService;
3131
private IURLGenerator $urlGenerator;
3232

33+
private Helper $helper;
34+
3335
public function __construct($appName,
3436
IRequest $request,
3537
AssetMapper $assetMapper,
3638
IRootFolder $rootFolder,
3739
$userId,
3840
UserScopeService $userScopeService,
39-
IURLGenerator $urlGenerator) {
41+
IURLGenerator $urlGenerator,
42+
Helper $helper,
43+
) {
4044
parent::__construct($appName, $request);
4145

4246
$this->assetMapper = $assetMapper;
4347
$this->rootFolder = $rootFolder;
4448
$this->userId = $userId;
4549
$this->userScopeService = $userScopeService;
4650
$this->urlGenerator = $urlGenerator;
51+
$this->helper = $helper;
4752
}
4853

4954
/**
@@ -63,14 +68,12 @@ public function create($path) {
6368
return new JSONResponse([], Http::STATUS_NOT_FOUND);
6469
}
6570

66-
$storage = $node->getStorage();
67-
if ($storage->instanceOfStorage(SharedStorage::class)) {
68-
/** @var SharedStorage $storage */
69-
$share = $storage->getShare();
70-
$attributes = $share->getAttributes();
71-
if ($attributes !== null && $attributes->getAttribute('permissions', 'download') === false) {
72-
throw new NotPermittedException();
73-
}
71+
$share = $this->helper->getShareFromNode($node);
72+
$attributes = $share?->getAttributes();
73+
if ($attributes !== null
74+
&& $attributes->getAttribute('permissions', 'download') === false
75+
) {
76+
throw new NotPermittedException();
7477
}
7578
} catch (NotFoundException $e) {
7679
return new JSONResponse([], Http::STATUS_NOT_FOUND);

lib/Controller/WopiController.php

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -82,7 +82,8 @@ public function __construct(
8282
private IEncryptionManager $encryptionManager,
8383
private IGroupManager $groupManager,
8484
private ILockManager $lockManager,
85-
private IEventDispatcher $eventDispatcher
85+
private IEventDispatcher $eventDispatcher,
86+
private Helper $helper,
8687
) {
8788
parent::__construct($appName, $request);
8889
}
@@ -187,7 +188,7 @@ public function checkFileInfo($fileId, $access_token) {
187188
$response['TemplateSource'] = $this->getWopiUrlForTemplate($wopi);
188189
}
189190

190-
$share = $this->getShareForWopiToken($wopi);
191+
$share = $this->getShareForWopiToken($wopi, $file);
191192
if ($this->permissionManager->shouldWatermark($file, $wopi->getEditorUid(), $share)) {
192193
$email = $user !== null && !$isPublic ? $user->getEMailAddress() : '';
193194
$replacements = [
@@ -804,10 +805,14 @@ private function getFileForWopiToken(Wopi $wopi) {
804805
return array_shift($files);
805806
}
806807

807-
private function getShareForWopiToken(Wopi $wopi): ?IShare {
808+
private function getShareForWopiToken(Wopi $wopi, File $file): ?IShare {
808809
try {
809-
return $wopi->getShare() ? $this->shareManager->getShareByToken($wopi->getShare()) : null;
810-
} catch (ShareNotFound $e) {
810+
$shareToken = $wopi->getShare();
811+
if ($shareToken) {
812+
return $this->shareManager->getShareByToken($shareToken);
813+
}
814+
return $this->helper->getShareFromNode($file);
815+
} catch (ShareNotFound) {
811816
}
812817

813818
return null;

lib/Helper.php

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,11 @@
77

88
use DateTime;
99
use DateTimeZone;
10+
use OCA\Files_Sharing\SharedStorage;
1011
use OCP\Files\Folder;
12+
use OCP\Files\Node;
13+
use OCP\Files\NotFoundException;
14+
use OCP\Share\IShare;
1115

1216
class Helper {
1317
/** @var string|null */
@@ -81,4 +85,17 @@ public function getGuestNameFromCookie() {
8185
}
8286
return $_COOKIE['guestUser'];
8387
}
88+
89+
public function getShareFromNode(Node $node): ?IShare {
90+
try {
91+
$storage = $node->getStorage();
92+
} catch (NotFoundException) {
93+
return null;
94+
}
95+
if ($storage->instanceOfStorage(SharedStorage::class)) {
96+
/** @var SharedStorage $storage */
97+
return $storage->getShare();
98+
}
99+
return null;
100+
}
84101
}

lib/Listener/BeforeFetchPreviewListener.php

Lines changed: 10 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010

1111
namespace OCA\Richdocuments\Listener;
1212

13-
use OCA\Files_Sharing\SharedStorage;
13+
use OCA\Richdocuments\Helper;
1414
use OCA\Richdocuments\PermissionManager;
1515
use OCP\EventDispatcher\Event;
1616
use OCP\EventDispatcher\IEventListener;
@@ -20,20 +20,21 @@
2020
use OCP\Preview\BeforePreviewFetchedEvent;
2121
use OCP\Share\Exceptions\ShareNotFound;
2222
use OCP\Share\IManager;
23-
use OCP\Share\IShare;
2423

2524
/** @template-implements IEventListener<Event|BeforePreviewFetchedEvent> */
2625
class BeforeFetchPreviewListener implements IEventListener {
2726
private PermissionManager $permissionManager;
2827
private IUserSession $userSession;
2928
private IRequest $request;
3029
private IManager $shareManager;
30+
private Helper $helper;
3131

32-
public function __construct(PermissionManager $permissionManager, IUserSession $userSession, IRequest $request, IManager $shareManager) {
32+
public function __construct(PermissionManager $permissionManager, IUserSession $userSession, IRequest $request, IManager $shareManager, Helper $helper) {
3333
$this->permissionManager = $permissionManager;
3434
$this->userSession = $userSession;
3535
$this->request = $request;
3636
$this->shareManager = $shareManager;
37+
$this->helper = $helper;
3738
}
3839

3940
public function handle(Event $event): void {
@@ -42,21 +43,13 @@ public function handle(Event $event): void {
4243
}
4344
$shareToken = $this->request->getParam('token');
4445

45-
$share = null;
46-
47-
// Get share for internal shares
48-
$storage = $event->getNode()->getStorage();
49-
if (!$shareToken && $storage->instanceOfStorage(SharedStorage::class)) {
50-
if (method_exists(IShare::class, 'getAttributes')) {
51-
/** @var SharedStorage $storage */
52-
$share = $storage->getShare();
53-
}
54-
}
55-
56-
// Get different share for public previews as the share from the node is only set for mounted shares
5746
try {
58-
$share = $shareToken ? $this->shareManager->getShareByToken($shareToken) : $share;
59-
} catch (ShareNotFound $e) {
47+
$share = $shareToken ?
48+
// Get different share for public previews as the share from the node is only set for mounted shares
49+
$this->shareManager->getShareByToken($shareToken)
50+
// Get share for internal shares
51+
: $this->helper->getShareFromNode($event->getNode());
52+
} catch (ShareNotFound) {
6053
}
6154

6255
$userId = $this->userSession->getUser() ? $this->userSession->getUser()->getUID() : null;

lib/TokenManager.php

Lines changed: 7 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@
77
namespace OCA\Richdocuments;
88

99
use Exception;
10-
use OCA\Files_Sharing\SharedStorage;
1110
use OCA\Richdocuments\Db\Direct;
1211
use OCA\Richdocuments\Db\Wopi;
1312
use OCA\Richdocuments\Db\WopiMapper;
@@ -24,7 +23,6 @@
2423
use OCP\IURLGenerator;
2524
use OCP\Share\Exceptions\ShareNotFound;
2625
use OCP\Share\IManager;
27-
use OCP\Share\IShare;
2826
use OCP\Util;
2927
use Psr\Log\LoggerInterface;
3028

@@ -83,19 +81,13 @@ public function generateWopiToken(string $fileId, ?string $shareToken = null, ?s
8381

8482
// disable download if at least one shared access has it disabled
8583
foreach ($files as $file) {
86-
$storage = $file->getStorage();
87-
// using string as we have no guarantee that "files_sharing" app is loaded
88-
if ($storage->instanceOfStorage(SharedStorage::class)) {
89-
if (!method_exists(IShare::class, 'getAttributes')) {
90-
break;
91-
}
92-
/** @var SharedStorage $storage */
93-
$share = $storage->getShare();
94-
$attributes = $share->getAttributes();
95-
if ($attributes !== null && $attributes->getAttribute('permissions', 'download') === false) {
96-
$hideDownload = true;
97-
break;
98-
}
84+
$share = $this->helper->getShareFromNode($file);
85+
$attributes = $share?->getAttributes();
86+
if ($attributes !== null
87+
&& $attributes->getAttribute('permissions', 'download') === false
88+
) {
89+
$hideDownload = true;
90+
break;
9991
}
10092
}
10193
}

0 commit comments

Comments
 (0)