Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/nextcloud/richdocuments.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorJulius Härtl <jus@bitgrid.net>2019-07-04 17:48:35 +0300
committerJulius Härtl <jus@bitgrid.net>2019-08-27 19:39:52 +0300
commit9b3fb584fb1c9fb7ce506a0797f061be07320833 (patch)
tree50de5d9d004486cf9027fc50db36f0ae0bb4f389 /lib
parent8ea1b34a2f5ed910fce4ebd68749f49ae1f3243d (diff)
PoC: Federated document editing
Signed-off-by: Julius Härtl <jus@bitgrid.net>
Diffstat (limited to 'lib')
-rw-r--r--lib/Controller/DocumentController.php144
-rw-r--r--lib/Controller/FederationController.php121
-rw-r--r--lib/Controller/OCSController.php31
-rw-r--r--lib/Controller/WopiController.php8
-rw-r--r--lib/Db/Wopi.php9
-rw-r--r--lib/Db/WopiMapper.php14
-rw-r--r--lib/Service/FederationService.php116
-rw-r--r--lib/TokenManager.php20
8 files changed, 438 insertions, 25 deletions
diff --git a/lib/Controller/DocumentController.php b/lib/Controller/DocumentController.php
index 5e1fb762..6ddd97bf 100644
--- a/lib/Controller/DocumentController.php
+++ b/lib/Controller/DocumentController.php
@@ -11,11 +11,15 @@
namespace OCA\Richdocuments\Controller;
+use OCA\Richdocuments\Db\WopiMapper;
+use OCA\Richdocuments\Service\FederationService;
use OCA\Richdocuments\TokenManager;
use OCA\Richdocuments\WOPI\Parser;
use \OCP\AppFramework\Controller;
use OCP\AppFramework\Http;
use OCP\AppFramework\Http\JSONResponse;
+use OCP\AppFramework\Http\RedirectResponse;
+use OCP\Constants;
use OCP\Files\Folder;
use OCP\Files\IRootFolder;
use OCP\Files\Node;
@@ -54,10 +58,11 @@ class DocumentController extends Controller {
private $rootFolder;
/** @var \OCA\Richdocuments\TemplateManager */
private $templateManager;
+ /** @var FederationService */
+ private $federationService;
const ODT_TEMPLATE_PATH = '/assets/odttemplate.odt';
-
/**
* @param string $appName
* @param IRequest $request
@@ -71,18 +76,21 @@ class DocumentController extends Controller {
* @param string $UserId
* @param ILogger $logger
*/
- public function __construct($appName,
- IRequest $request,
- IConfig $settings,
- AppConfig $appConfig,
- IL10N $l10n,
- IManager $shareManager,
- TokenManager $tokenManager,
- IRootFolder $rootFolder,
- ISession $session,
- $UserId,
- ILogger $logger,
- \OCA\Richdocuments\TemplateManager $templateManager) {
+ public function __construct(
+ $appName,
+ IRequest $request,
+ IConfig $settings,
+ AppConfig $appConfig,
+ IL10N $l10n,
+ IManager $shareManager,
+ TokenManager $tokenManager,
+ IRootFolder $rootFolder,
+ ISession $session,
+ $UserId,
+ ILogger $logger,
+ \OCA\Richdocuments\TemplateManager $templateManager,
+ FederationService $federationService
+ ) {
parent::__construct($appName, $request);
$this->uid = $UserId;
$this->l10n = $l10n;
@@ -94,6 +102,7 @@ class DocumentController extends Controller {
$this->session = $session;
$this->logger = $logger;
$this->templateManager = $templateManager;
+ $this->federationService = $federationService;
}
/**
@@ -164,7 +173,7 @@ class DocumentController extends Controller {
* @NoAdminRequired
*
* @param string $fileId
- * @return TemplateResponse
+ * @return RedirectResponse|TemplateResponse
*/
public function index($fileId) {
try {
@@ -173,6 +182,25 @@ class DocumentController extends Controller {
if(!($item instanceof Node)) {
throw new \Exception();
}
+ /**
+ * Open file from remote collabora
+ */
+ if ($item->getStorage()->instanceOfStorage(\OCA\Files_Sharing\External\Storage::class)) {
+ $remote = $item->getStorage()->getRemote();
+ $remoteCollabora = $this->federationService->getRemoteCollaboraURL($remote);
+ if ($remoteCollabora !== '') {
+ $wopi = $this->tokenManager->getRemoteToken($item);
+ $url = $remote . 'index.php/apps/richdocuments/remote?shareToken=' . $item->getStorage()->getToken() .
+ '&remoteServer=' . $wopi->getServerHost() .
+ '&remoteServerToken=' . $wopi->getToken();
+ if ($item->getInternalPath() !== '') {
+ $url .= '&filePath=' . $item->getInternalPath();
+ }
+ $response = new RedirectResponse($url);
+ $response->addHeader('X-Frame-Options', 'ALLOW');
+ return $response;
+ }
+ }
list($urlSrc, $token) = $this->tokenManager->getToken($item->getId());
$params = [
'permissions' => $item->getPermissions(),
@@ -217,10 +245,15 @@ class DocumentController extends Controller {
/**
* @NoAdminRequired
*
+ * Create a new file from a template
+ *
* @param int $templateId
* @param string $fileName
* @param string $dir
* @return TemplateResponse
+ * @throws NotFoundException
+ * @throws NotPermittedException
+ * @throws \OCP\Files\InvalidPathException
*/
public function template($templateId, $fileName, $dir) {
if (!$this->templateManager->isTemplate($templateId)) {
@@ -265,6 +298,7 @@ class DocumentController extends Controller {
/**
* @PublicPage
+ * @NoCSRFRequired
*
* @param string $shareToken
* @param string $fileName
@@ -321,6 +355,88 @@ class DocumentController extends Controller {
}
/**
+ * @PublicPage
+ * @NoCSRFRequired
+ *
+ * @param string $shareToken
+ * @param string $remoteWopiToken
+ * @return TemplateResponse
+ * @throws \Exception
+ */
+ // TODO: we need to use the file apth instead of the file id, since the id is not available on remote servers
+ public function remote($shareToken, $remoteServer, $remoteServerToken, $filePath = null) {
+ $manager = \OC::$server->getContentSecurityPolicyManager();
+ $policy = new \OC\Security\CSP\ContentSecurityPolicy();
+ $policy->addAllowedFrameAncestorDomain('https://*');
+ $manager->addDefaultPolicy($policy);
+
+ try {
+ $share = $this->shareManager->getShareByToken($shareToken);
+ // not authenticated ?
+ if($share->getPassword()){
+ if (!$this->session->exists('public_link_authenticated')
+ || $this->session->get('public_link_authenticated') !== (string)$share->getId()
+ ) {
+ throw new \Exception('Invalid password');
+ }
+ }
+
+ $node = $share->getNode();
+ if ($filePath !== null) {
+ $node = $node->get($filePath);
+ }
+
+ if ($node instanceof Node) {
+ list($urlSrc, $token, $wopi) = $this->tokenManager->getToken($node->getId(), $shareToken, $this->uid);
+
+ $remoteWopi = $this->federationService->getRemoteFileDetails($remoteServer, $remoteServerToken);
+
+ $uid = $remoteWopi['editorUid'] . '@' . $remoteServer;
+ $wopi->setEditorUid($remoteWopi['editorUid']);
+ $wopi->setCanwrite($wopi->getCanwrite() && $remoteWopi['canwrite']);
+ $wopi->setRemoteServer($remoteServer);
+ $wopi->setRemoteServerToken($remoteServerToken);
+ $wopi->setGuestDisplayname($uid);
+ $mapper = \OC::$server->query(WopiMapper::class);
+ $mapper->update($wopi);
+
+ $permissions = $share->getPermissions();
+ if (!$remoteWopi['canwrite']) {
+ $permissions = $permissions & ~ Constants::PERMISSION_UPDATE;
+ }
+
+ $params = [
+ 'permissions' => $permissions,
+ 'title' => $node->getName(),
+ 'fileId' => $node->getId() . '_' . $this->settings->getSystemValue('instanceid'),
+ 'token' => $token,
+ 'urlsrc' => $urlSrc,
+ 'path' => '/',
+ 'instanceId' => $this->settings->getSystemValue('instanceid'),
+ 'canonical_webroot' => $this->appConfig->getAppValue('canonical_webroot'),
+ 'userId' => $uid
+ ];
+
+ $response = new TemplateResponse('richdocuments', 'documents', $params, 'empty');
+ $policy = new ContentSecurityPolicy();
+ $policy->addAllowedFrameDomain($this->domainOnly($this->appConfig->getAppValue('wopi_url')));
+ $policy->allowInlineScript(true);
+ $response->setContentSecurityPolicy($policy);
+ $response->addHeader('X-Frame-Options', 'ALLOW');
+ return $response;
+ }
+ } catch (\Exception $e) {
+ $this->logger->logException($e, ['app'=>'richdocuments']);
+ $params = [
+ 'errors' => [['error' => $e->getMessage()]]
+ ];
+ return new TemplateResponse('core', 'error', $params, 'guest');
+ }
+
+ return new TemplateResponse('core', '403', [], 'guest');
+ }
+
+ /**
* @NoAdminRequired
*
* @param string $mimetype
diff --git a/lib/Controller/FederationController.php b/lib/Controller/FederationController.php
new file mode 100644
index 00000000..eb26d334
--- /dev/null
+++ b/lib/Controller/FederationController.php
@@ -0,0 +1,121 @@
+<?php
+/**
+ * @copyright Copyright (c) 2019 Julius Härtl <jus@bitgrid.net>
+ *
+ * @author Julius Härtl <jus@bitgrid.net>
+ *
+ * @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 <http://www.gnu.org/licenses/>.
+ *
+ */
+namespace OCA\Richdocuments\Controller;
+
+
+use OCA\Richdocuments\Db\WopiMapper;
+use OCP\AppFramework\Http\DataResponse;
+use OCP\AppFramework\OCS\OCSNotFoundException;
+use OCP\IConfig;
+use OCP\IRequest;
+
+class FederationController extends \OCP\AppFramework\OCSController {
+
+ /** @var IConfig */
+ private $config;
+
+
+ public function __construct(
+ string $appName,
+ IRequest $request,
+ IConfig $config,
+ WopiMapper $wopiMapper
+ ) {
+ parent::__construct($appName, $request);
+ $this->config = $config;
+ $this->wopiMapper = $wopiMapper;
+ }
+
+ /**
+ * @PublicPage
+ * @NoCSRFRequired
+ */
+ public function index() {
+ return new DataResponse([
+ 'wopi_url' => $this->config->getAppValue('richdocuments', 'wopi_url')
+ ]);
+ }
+
+ /**
+ * @PublicPage
+ * @NoCSRFRequired
+ *
+ * Check the file info of a remote accessing a file
+ *
+ * this is used to make sure we respect reshares of federated shares with the
+ * applied permissions and also have information about the actual editor
+ *
+ * @param $token
+ * @return DataResponse
+ * @throws \OCP\AppFramework\Db\DoesNotExistException
+ */
+ public function remoteWopiToken($token) {
+ $wopi = $this->wopiMapper->getWopiForToken($token);
+ return new DataResponse([
+ 'ownerUid' => $wopi->getOwnerUid(),
+ 'editorUid' => $wopi->getEditorUid(),
+ 'canwrite' => $wopi->getCanwrite(),
+ 'hideDownload' => $wopi->getHideDownload(),
+ 'direct' => $wopi->getDirect(),
+ 'serverHost' => $wopi->getServerHost(),
+ 'guestDisplayname' => $wopi->getGuestDisplayname()
+ ]);
+ }
+
+ /**
+ * @PublicPage
+ * @NoCSRFRequired
+ *
+ * Check the file info of a remote accessing a file
+ *
+ * this is used to make sure we respect reshares of federated shares with the
+ * applied permissions and also have information about the actual editor
+ *
+ * @param $shareToken
+ * @param $filePath
+ * @return DataResponse
+ * @throws OCSNotFoundException
+ * @throws \OCP\Files\NotFoundException
+ * @throws \OCP\Share\Exceptions\ShareNotFound
+ */
+ private function remoteDirectToken($shareToken, $filePath) {
+ $this->shareManager = \OC::$server->getShareManager();
+ try {
+ $share = $this->shareManager->getShareByToken($shareToken);
+ $file = $share->getNode()->get($filePath);
+ //TODO check if we can even edit this file with collabora
+ $direct = $this->directMapper->newDirect($this->userId, $file);
+ // TODO: convert to remote token if needed
+
+ return new DataResponse([
+ 'url' => $this->urlGenerator->linkToRouteAbsolute('richdocuments.directView.show', [
+ 'token' => $direct->getToken()
+ ])
+ ]);
+ } catch (NotFoundException $e) {
+ throw new OCSNotFoundException();
+ }
+ }
+
+
+}
diff --git a/lib/Controller/OCSController.php b/lib/Controller/OCSController.php
index 7b9b70cf..fe1e9de5 100644
--- a/lib/Controller/OCSController.php
+++ b/lib/Controller/OCSController.php
@@ -24,6 +24,7 @@
namespace OCA\Richdocuments\Controller;
use OCA\Richdocuments\Db\DirectMapper;
+use OCA\Richdocuments\Service\FederationService;
use OCA\Richdocuments\TemplateManager;
use OCP\AppFramework\Http\DataResponse;
use OCP\AppFramework\OCS\OCSBadRequestException;
@@ -52,6 +53,9 @@ class OCSController extends \OCP\AppFramework\OCSController {
/** @var TemplateManager */
private $manager;
+ /** @var FederationService */
+ private $federationService;
+
/**
* OCS controller
*
@@ -69,7 +73,9 @@ class OCSController extends \OCP\AppFramework\OCSController {
$userId,
DirectMapper $directMapper,
IURLGenerator $urlGenerator,
- TemplateManager $manager) {
+ TemplateManager $manager,
+ FederationService $federationService
+ ) {
parent::__construct($appName, $request);
$this->rootFolder = $rootFolder;
@@ -77,6 +83,7 @@ class OCSController extends \OCP\AppFramework\OCSController {
$this->directMapper = $directMapper;
$this->urlGenerator = $urlGenerator;
$this->manager = $manager;
+ $this->federationService = $federationService;
}
/**
@@ -102,9 +109,29 @@ class OCSController extends \OCP\AppFramework\OCSController {
throw new OCSBadRequestException('Cannot view folder');
}
- //TODO check if we can even edit this file with collabora
+ /**
+ * Open file from remote collabora
+ */
+ if ($node->getStorage()->instanceOfStorage(\OCA\Files_Sharing\External\Storage::class)) {
+ $remote = $node->getStorage()->getRemote();
+ $remoteCollabora = $this->federationService->getRemoteDirectToken($remote);
+ if ($remoteCollabora !== '') {
+ $wopi = $this->tokenManager->getRemoteToken($item);
+ $url = $remote . 'index.php/apps/richdocuments/remote?shareToken=' . $item->getStorage()->getToken() .
+ '&remoteServer=' . $wopi->getServerHost() .
+ '&remoteServerToken=' . $wopi->getToken();
+ if ($item->getInternalPath() !== '') {
+ $url .= '&filePath=' . $item->getInternalPath();
+ }
+ $response = new RedirectResponse($url);
+ $response->addHeader('X-Frame-Options', 'ALLOW');
+ return $response;
+ }
+ }
+ //TODO check if we can even edit this file with collabora
$direct = $this->directMapper->newDirect($this->userId, $fileId);
+ // TODO: convert to remote token if needed
return new DataResponse([
'url' => $this->urlGenerator->linkToRouteAbsolute('richdocuments.directView.show', [
diff --git a/lib/Controller/WopiController.php b/lib/Controller/WopiController.php
index 6aae1d4d..62c6ab6a 100644
--- a/lib/Controller/WopiController.php
+++ b/lib/Controller/WopiController.php
@@ -116,7 +116,7 @@ class WopiController extends Controller {
list($fileId, , $version) = Helper::parseFileId($fileId);
try {
- $wopi = $this->wopiMapper->getPathForToken($access_token);
+ $wopi = $this->wopiMapper->getWopiForToken($access_token);
} catch (DoesNotExistException $e) {
return new JSONResponse([], Http::STATUS_FORBIDDEN);
}
@@ -199,7 +199,7 @@ class WopiController extends Controller {
$access_token) {
list($fileId, , $version) = Helper::parseFileId($fileId);
- $wopi = $this->wopiMapper->getPathForToken($access_token);
+ $wopi = $this->wopiMapper->getWopiForToken($access_token);
if ((int)$fileId !== $wopi->getFileid()) {
return new JSONResponse([], Http::STATUS_FORBIDDEN);
@@ -262,7 +262,7 @@ class WopiController extends Controller {
$isPutRelative = ($this->request->getHeader('X-WOPI-Override') === 'PUT_RELATIVE');
$isRenameFile = ($this->request->getHeader('X-WOPI-Override') === 'RENAME_FILE');
- $wopi = $this->wopiMapper->getPathForToken($access_token);
+ $wopi = $this->wopiMapper->getWopiForToken($access_token);
if (!$wopi->getCanwrite()) {
return new JSONResponse([], Http::STATUS_FORBIDDEN);
}
@@ -370,7 +370,7 @@ class WopiController extends Controller {
public function putRelativeFile($fileId,
$access_token) {
list($fileId, ,) = Helper::parseFileId($fileId);
- $wopi = $this->wopiMapper->getPathForToken($access_token);
+ $wopi = $this->wopiMapper->getWopiForToken($access_token);
$isRenameFile = ($this->request->getHeader('X-WOPI-Override') === 'RENAME_FILE');
if (!$wopi->getCanwrite()) {
diff --git a/lib/Db/Wopi.php b/lib/Db/Wopi.php
index eff47a03..f8d8143b 100644
--- a/lib/Db/Wopi.php
+++ b/lib/Db/Wopi.php
@@ -87,6 +87,15 @@ class Wopi extends Entity {
/** @var bool */
protected $direct;
+ /** @var bool */
+ protected $isRemoteToken;
+
+ /** @var string */
+ protected $remoteServer;
+
+ /** @var string */
+ protected $remoteServerToken;
+
public function __construct() {
$this->addType('owner_uid', 'string');
$this->addType('editor_uid', 'string');
diff --git a/lib/Db/WopiMapper.php b/lib/Db/WopiMapper.php
index f89ae449..e9056730 100644
--- a/lib/Db/WopiMapper.php
+++ b/lib/Db/WopiMapper.php
@@ -64,7 +64,7 @@ class WopiMapper extends Mapper {
* @param int $templateDestination
* @return Wopi
*/
- public function generateFileToken($fileId, $owner, $editor, $version, $updatable, $serverHost, $guestDisplayname, $templateDestination = 0, $hideDownload = false, $direct = false) {
+ public function generateFileToken($fileId, $owner, $editor, $version, $updatable, $serverHost, $guestDisplayname, $templateDestination = 0, $hideDownload = false, $direct = false, $isRemoteToken = false) {
$token = $this->random->generate(32, ISecureRandom::CHAR_LOWER . ISecureRandom::CHAR_UPPER . ISecureRandom::CHAR_DIGITS);
$wopi = Wopi::fromParams([
@@ -79,7 +79,8 @@ class WopiMapper extends Mapper {
'guestDisplayname' => $guestDisplayname,
'templateDestination' => $templateDestination,
'hideDownload' => $hideDownload,
- 'direct' => $direct
+ 'direct' => $direct,
+ 'isRemoteToken' => $isRemoteToken
]);
/** @var Wopi $wopi */
@@ -89,6 +90,13 @@ class WopiMapper extends Mapper {
}
/**
+ * @deprecated
+ * @param $token
+ */
+ public function getPathForToken($token) {
+ return $this->getWopiForToken($token);
+ }
+ /**
* Given a token, validates it and
* constructs and validates the path.
* Returns the path, if valid, else false.
@@ -97,7 +105,7 @@ class WopiMapper extends Mapper {
* @throws DoesNotExistException
* @return Wopi
*/
- public function getPathForToken($token) {
+ public function getWopiForToken($token) {
$qb = $this->db->getQueryBuilder();
$qb->select('*')
diff --git a/lib/Service/FederationService.php b/lib/Service/FederationService.php
new file mode 100644
index 00000000..8b2e775d
--- /dev/null
+++ b/lib/Service/FederationService.php
@@ -0,0 +1,116 @@
+<?php
+/**
+ * @copyright Copyright (c) 2019 Julius Härtl <jus@bitgrid.net>
+ *
+ * @author Julius Härtl <jus@bitgrid.net>
+ *
+ * @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 <http://www.gnu.org/licenses/>.
+ *
+ */
+
+namespace OCA\Richdocuments\Service;
+
+
+use OCA\Federation\TrustedServers;
+use OCP\AppFramework\QueryException;
+use OCP\Http\Client\IClientService;
+use OCP\ICache;
+use OCP\ILogger;
+
+class FederationService {
+
+ /** @var ICache */
+ private $cache;
+ /** @var IClientService */
+ private $clientService;
+ /** @var ILogger */
+ private $logger;
+ /** @var TrustedServers */
+ private $trustedServers;
+
+ public function __construct(ICache $cache, IClientService $clientService, ILogger $logger) {
+ $this->cache = $cache;
+ $this->clientService = $clientService;
+ $this->logger = $logger;
+ try {
+ $this->trustedServers = \OC::$server->query( \OCA\Federation\TrustedServers::class);
+ } catch (QueryException $e) {}
+ }
+
+ public function getRemoteCollaboraURL($remote) {
+ if ($this->trustedServers === null || !$this->trustedServers->isTrustedServer($remote)) {
+ $this->logger->info('Unable to determine collabora URL of remote server ' . $remote . ' - Remote is not a trusted server');
+ return '';
+ }
+ if ($remoteCollabora = $this->cache->get('richdocuments_remote/' . $remote)) {
+ return $remoteCollabora;
+ }
+ try {
+ $client = $this->clientService->newClient();
+ $response = $client->get($remote . '/ocs/v2.php/apps/richdocuments/api/v1/federation?format=json', ['timeout' => 5]);
+ $data = \json_decode($response->getBody(), true);
+ $remoteCollabora = $data['ocs']['data']['wopi_url'];
+ $this->cache->get('richdocuments_remote/' . $remote, $remoteCollabora, 3600);
+ return $remoteCollabora;
+ } catch (\Throwable $e) {
+ $this->logger->info('Unable to determine collabora URL of remote server ' . $remote);
+ $this->cache->get('richdocuments_remote/' . $remote, '', 300);
+ }
+ return '';
+ }
+
+ public function getRemoteDirectUrl($remote, $shareToken, $filePath) {
+ if ($this->getRemoteCollaboraURL() === '') {
+ return '';
+ }
+ try {
+ $client = $this->clientService->newClient();
+ $response = $client->post($remote . '/ocs/v2.php/apps/richdocuments/api/v1/federation/direct?format=json', [
+ 'timeout' => 5,
+ 'body' => [
+ 'shareToken' => $shareToken,
+ 'filePath' => $filePath
+ ]
+ ]);
+ $data = \json_decode($response->getBody(), true);
+ return $data['ocs']['data'];
+ } catch (\Throwable $e) {
+ $this->logger->info('Unable to determine collabora URL of remote server ' . $remote);
+ }
+ return null;
+ }
+
+ public function getRemoteFileDetails($remote, $remoteToken) {
+ if ($this->trustedServers === null || !$this->trustedServers->isTrustedServer($remote)) {
+ $this->logger->info('Unable to determine collabora URL of remote server ' . $remote . ' - Remote is not a trusted server');
+ return null;
+ }
+ try {
+ $client = $this->clientService->newClient();
+ $response = $client->post($remote . '/ocs/v2.php/apps/richdocuments/api/v1/federation?format=json', [
+ 'timeout' => 5,
+ 'body' => [
+ 'token' => $remoteToken
+ ]
+ ]);
+ $data = \json_decode($response->getBody(), true);
+ return $data['ocs']['data'];
+ } catch (\Throwable $e) {
+ $this->logger->info('Unable to determine collabora URL of remote server ' . $remote);
+ }
+ return null;
+ }
+}
diff --git a/lib/TokenManager.php b/lib/TokenManager.php
index 5b60b577..f73141f6 100644
--- a/lib/TokenManager.php
+++ b/lib/TokenManager.php
@@ -28,9 +28,11 @@ use OCA\Richdocuments\Db\Wopi;
use OCA\Richdocuments\WOPI\Parser;
use OCP\Files\File;
use OCP\Files\IRootFolder;
+use OCP\Files\Node;
use OCP\IGroupManager;
use OCP\IURLGenerator;
use OCP\IUserManager;
+use OCP\Security\ISecureRandom;
use OCP\Share\IManager;
use OCP\IL10N;
use OCP\Util;
@@ -96,7 +98,7 @@ class TokenManager {
* @return array
* @throws \Exception
*/
- public function getToken($fileId, $shareToken = null, $editoruid = null, $direct = false) {
+ public function getToken($fileId, $shareToken = null, $editoruid = null, $direct = false, $isRemoteToken = false) {
list($fileId,, $version) = Helper::parseFileId($fileId);
$owneruid = null;
$hideDownload = false;
@@ -173,13 +175,14 @@ class TokenManager {
$guest_name = NULL;
}
- $wopi = $this->wopiMapper->generateFileToken($fileId, $owneruid, $editoruid, $version, (int)$updatable, $serverHost, $guest_name, 0, $hideDownload, $direct);
+ $wopi = $this->wopiMapper->generateFileToken($fileId, $owneruid, $editoruid, $version, (int)$updatable, $serverHost, $guest_name, 0, $hideDownload, $direct, $isRemoteToken);
try {
return [
$this->wopiParser->getUrlSrc($file->getMimeType())['urlsrc'],
$wopi->getToken(),
+ $wopi
];
} catch (\Exception $e){
throw $e;
@@ -216,4 +219,17 @@ class TokenManager {
$wopi->getToken(),
];
}
+
+ /**
+ * @param Node $node
+ * @return Wopi
+ */
+ public function getRemoteToken(Node $node) {
+ list($urlSrc, $token, $wopi) = $this->getToken($node->getId(), null, null, false, true);
+ $wopi->setIsRemoteToken(true);
+ $wopi->setRemoteServer($node->getStorage()->getRemote());
+
+ $this->wopiMapper->update($wopi);
+ return $wopi;
+ }
}