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>2021-04-26 13:23:17 +0300
committerJulius Härtl <jus@bitgrid.net>2021-04-28 11:40:59 +0300
commit49fd9ac1d620b036c436ed7b2d382db754533a61 (patch)
tree9d7e48d1a01d8466afed736c52d89abf2fe5706f /lib
parenta9b794a971af44332c304a33d3e632b49e99fd49 (diff)
Allow fetching the initiator user data if needed
Signed-off-by: Julius Härtl <jus@bitgrid.net>
Diffstat (limited to 'lib')
-rw-r--r--lib/Controller/FederationController.php56
-rw-r--r--lib/Controller/OCSController.php2
-rw-r--r--lib/Controller/WopiController.php34
-rw-r--r--lib/Service/FederationService.php19
-rw-r--r--lib/TokenManager.php15
5 files changed, 85 insertions, 41 deletions
diff --git a/lib/Controller/FederationController.php b/lib/Controller/FederationController.php
index 8a0f9277..08fd39c7 100644
--- a/lib/Controller/FederationController.php
+++ b/lib/Controller/FederationController.php
@@ -30,6 +30,8 @@ use OCP\AppFramework\Http\DataResponse;
use OCP\IConfig;
use OCP\ILogger;
use OCP\IRequest;
+use OCP\IURLGenerator;
+use OCP\IUserManager;
class FederationController extends OCSController {
@@ -42,17 +44,27 @@ class FederationController extends OCSController {
/** @var WopiMapper */
private $wopiMapper;
+ /** @var IUserManager */
+ private $userManager;
+
+ /** @var IURLGenerator */
+ private $urlGenerator;
+
public function __construct(
string $appName,
IRequest $request,
IConfig $config,
ILogger $logger,
- WopiMapper $wopiMapper
+ WopiMapper $wopiMapper,
+ IUserManager $userManager,
+ IURLGenerator $urlGenerator
) {
parent::__construct($appName, $request);
$this->config = $config;
$this->logger = $logger;
$this->wopiMapper = $wopiMapper;
+ $this->userManager = $userManager;
+ $this->urlGenerator = $urlGenerator;
}
/**
@@ -84,32 +96,54 @@ class FederationController extends OCSController {
*/
public function remoteWopiToken($token): DataResponse {
try {
- $wopi = $this->wopiMapper->getWopiForToken($token);
- $user = \OC::$server->getUserManager()->get($wopi->getEditorUid());
- if($user !== null) {
- $wopi->setGuestDisplayname($user->getDisplayName());
+ $initiatorWopi = $this->wopiMapper->getWopiForToken($token);
+ if (empty($initiatorWopi->getEditorUid()) && !empty($initiatorWopi->getRemoteServer()) && !empty($initiatorWopi->getRemoteServerToken())) {
+ $client = \OC::$server->getHTTPClientService()->newClient();
+ $response = $client->post(
+ rtrim($initiatorWopi->getRemoteServer(), '/') . '/ocs/v2.php/apps/richdocuments/api/v1/federation/user?format=json',
+ [ 'body' => [ 'token' => $initiatorWopi->getRemoteServerToken() ], 'timeout' => 10 ]
+ );
+ $initiatorUser = \json_decode($response->getBody(), true)['ocs']['data'];
+ $initiatorWopi->setGuestDisplayname($initiatorUser['displayName']);
+ } else {
+ $user = $this->userManager->get($initiatorWopi->getEditorUid());
+ if($user !== null) {
+ $initiatorWopi->setGuestDisplayname($user->getDisplayName());
+ }
}
$this->logger->debug('COOL-Federation-Initiator: Token ' . $token . ' returned');
- return new DataResponse($wopi);
+ return new DataResponse($initiatorWopi);
} catch (DoesNotExistException $e) {
$this->logger->debug('COOL-Federation-Initiator: Token ' . $token . 'not found');
throw new OCSNotFoundException();
}
}
+ /**
+ * @PublicPage
+ * @NoCSRFRequired
+ * @OCSRoute POST /api/v1/federation/user
+ *
+ * Return user details for a initiator user that will be used by remote instances
+ * to provide Collabora with the users avatar/displayname for guests on share links
+ * if the session was created through a direct link of a public share
+ *
+ * @param $token
+ * @return DataResponse
+ * @throws DoesNotExistException
+ */
public function initiatorUser($token): DataResponse {
try {
$wopi = $this->wopiMapper->getWopiForToken($token);
- $user = \OC::$server->getUserManager()->get($wopi->getEditorUid());
+ $user = $this->userManager->get($wopi->getEditorUid());
if($user !== null) {
$wopi->setGuestDisplayname($user->getDisplayName());
}
$this->logger->debug('COOL-Federation-Initiator-User: Token ' . $token . ' returned');
return new DataResponse([
- 'initiatorHost' => '',
- 'userId' => '',
- 'displayName' => '',
- 'avatar' => ''
+ 'userId' => $user->getUID(),
+ 'displayName' => $user->getDisplayName(),
+ 'avatar' => $this->urlGenerator->linkToRouteAbsolute('core.avatar.getAvatar', ['userId' => $wopi->getEditorUid(), 'size' => WopiController::WOPI_AVATAR_SIZE])
]);
} catch (DoesNotExistException $e) {
$this->logger->debug('COOL-Federation-Initiator-User: Token ' . $token . 'not found');
diff --git a/lib/Controller/OCSController.php b/lib/Controller/OCSController.php
index 23188a3c..c7cf7520 100644
--- a/lib/Controller/OCSController.php
+++ b/lib/Controller/OCSController.php
@@ -156,7 +156,7 @@ class OCSController extends \OCP\AppFramework\OCSController {
'path' => $path,
'password' => $password
],
- 'timeout' => 5
+ 'timeout' => 30
]);
$url = \json_decode($response->getBody(), true)['ocs']['data']['url'];
diff --git a/lib/Controller/WopiController.php b/lib/Controller/WopiController.php
index 5ee267d2..4634b0b2 100644
--- a/lib/Controller/WopiController.php
+++ b/lib/Controller/WopiController.php
@@ -85,6 +85,8 @@ class WopiController extends Controller {
// Signifies LOOL that document has been changed externally in this storage
const LOOL_STATUS_DOC_CHANGED = 1010;
+ const WOPI_AVATAR_SIZE = 32;
+
/**
* @param string $appName
* @param IRequest $request
@@ -230,7 +232,7 @@ class WopiController extends Controller {
$user = $this->userManager->get($wopi->getEditorUid());
if($user !== null) {
- $response['UserExtraInfo']['avatar'] = $this->urlGenerator->linkToRouteAbsolute('core.avatar.getAvatar', ['userId' => $wopi->getEditorUid(), 'size' => 32]);
+ $response['UserExtraInfo']['avatar'] = $this->urlGenerator->linkToRouteAbsolute('core.avatar.getAvatar', ['userId' => $wopi->getEditorUid(), 'size' => self::WOPI_AVATAR_SIZE]);
}
if ($wopi->isRemoteToken()) {
@@ -242,12 +244,14 @@ class WopiController extends Controller {
private function setFederationFileInfo(Wopi $wopi, $response) {
+ $response['UserId'] = 'Guest-' . \OC::$server->getSecureRandom()->generate(8);
+
if ($wopi->getTokenType() === Wopi::TOKEN_TYPE_REMOTE_USER) {
$remoteUserId = $wopi->getGuestDisplayname();
$cloudID = \OC::$server->getCloudIdManager()->resolveCloudId($remoteUserId);
$response['UserId'] = $cloudID->getDisplayId();
$response['UserFriendlyName'] = $cloudID->getDisplayId();
- $response['UserExtraInfo']['avatar'] = $this->urlGenerator->linkToRouteAbsolute('core.avatar.getAvatar', ['userId' => explode('@', $remoteUserId)[0], 'size' => 32]);
+ $response['UserExtraInfo']['avatar'] = $this->urlGenerator->linkToRouteAbsolute('core.avatar.getAvatar', ['userId' => explode('@', $remoteUserId)[0], 'size' => self::WOPI_AVATAR_SIZE]);
$cleanCloudId = str_replace(['http://', 'https://'], '', $cloudID->getId());
$addressBookEntries = \OC::$server->getContactsManager()->search($cleanCloudId, ['CLOUD']);
foreach ($addressBookEntries as $entry) {
@@ -260,24 +264,20 @@ class WopiController extends Controller {
}
}
}
- } else if ($wopi->getTokenType() === Wopi::TOKEN_TYPE_REMOTE_GUEST) {
- $response['UserId'] = 'Guest-' . \OC::$server->getSecureRandom()->generate(8);
}
-
$initiator = $this->federationService->getRemoteFileDetails($wopi->getRemoteServer(), $wopi->getRemoteServerToken());
- if ($initiator !== null) {
- if ($initiator->hasTemplateId()) {
- $templateUrl = $wopi->getRemoteServer() . '/index.php/apps/richdocuments/wopi/template/' . $initiator->getTemplateId() . '?access_token=' . $initiator->getToken();
- $response['TemplateSource'] = $templateUrl;
- }
- if ($wopi->getTokenType() === Wopi::TOKEN_TYPE_REMOTE_USER) {
- $response['UserExtraInfo']['avatar'] = $wopi->getRemoteServer() . '/index.php/avatar/' . $initiator->getEditorUid() . '/32';
- }
- if ($wopi->getTokenType() === Wopi::TOKEN_TYPE_REMOTE_GUEST && $initiator->getEditorUid()) {
- $response['UserFriendlyName'] = $initiator->getGuestDisplayname() . ' (Guest)';
- $response['UserExtraInfo']['avatar'] = $wopi->getRemoteServer() . '/index.php/avatar/' . $initiator->getEditorUid() . '/32';
- }
+ if ($initiator === null) {
+ return $response;
+ }
+
+ $response['UserFriendlyName'] = $initiator->getGuestDisplayname() . ' (Guest)';
+ if ($initiator->hasTemplateId()) {
+ $templateUrl = $wopi->getRemoteServer() . '/index.php/apps/richdocuments/wopi/template/' . $initiator->getTemplateId() . '?access_token=' . $initiator->getToken();
+ $response['TemplateSource'] = $templateUrl;
+ }
+ if ($wopi->getTokenType() === Wopi::TOKEN_TYPE_REMOTE_USER || ($wopi->getTokenType() === Wopi::TOKEN_TYPE_REMOTE_GUEST && $initiator->getEditorUid())) {
+ $response['UserExtraInfo']['avatar'] = $wopi->getRemoteServer() . '/index.php/avatar/' . $initiator->getEditorUid() . '/'. self::WOPI_AVATAR_SIZE;
}
return $response;
diff --git a/lib/Service/FederationService.php b/lib/Service/FederationService.php
index fa555c49..190c9c1e 100644
--- a/lib/Service/FederationService.php
+++ b/lib/Service/FederationService.php
@@ -28,6 +28,7 @@ use OCA\Federation\TrustedServers;
use OCA\Files_Sharing\External\Storage as SharingExternalStorage;
use OCA\Richdocuments\Db\Direct;
use OCA\Richdocuments\Db\Wopi;
+use OCA\Richdocuments\Db\WopiMapper;
use OCA\Richdocuments\TokenManager;
use OCP\AppFramework\Http\RedirectResponse;
use OCP\AppFramework\QueryException;
@@ -91,7 +92,7 @@ class FederationService {
}
try {
$client = $this->clientService->newClient();
- $response = $client->get($remote . '/ocs/v2.php/apps/richdocuments/api/v1/federation?format=json', ['timeout' => 5]);
+ $response = $client->get($remote . '/ocs/v2.php/apps/richdocuments/api/v1/federation?format=json', ['timeout' => 30]);
$data = \json_decode($response->getBody(), true);
$remoteCollabora = $data['ocs']['data']['wopi_url'];
$this->cache->set('richdocuments_remote/' . $remote, $remoteCollabora, 3600);
@@ -168,7 +169,7 @@ class FederationService {
$this->logger->debug('COOL-Federation-Source: Fetching remote file details from ' . $remote . ' for token ' . $remoteToken);
$client = $this->clientService->newClient();
$response = $client->post($remote . '/ocs/v2.php/apps/richdocuments/api/v1/federation?format=json', [
- 'timeout' => 5,
+ 'timeout' => 30,
'body' => [
'token' => $remoteToken
]
@@ -179,7 +180,7 @@ class FederationService {
$this->cache->set($cacheKey, $data['ocs']['data']);
return Wopi::fromParams($data['ocs']['data']);
} catch (\Throwable $e) {
- $this->logger->error('COOL-Federation-Source: Unable to fetch remote file details for ' . $remoteToken . ' from ' . $remote, ['exception' => $e]);
+ $this->logger->logException($e, ['message' => 'COOL-Federation-Source: Unable to fetch remote file details for ' . $remoteToken . ' from ' . $remote ]);
}
return null;
}
@@ -204,12 +205,12 @@ class FederationService {
$initiatorServer = $wopi->getServerHost();
$initiatorToken = $wopi->getToken();
- if ($direct) {
- //$wopi->setRemoteServer($direct->getInitiatorHost());
- //$wopi->setRemoteServerToken($direct->getInitiatorToken());
- // FIXME: the direct token might have a different originator when a share link originating on a federated stoarge is opened
- // editor uid is null since we don't fetch it from the initiator of direct so @{link remoteWopiToken()} fails
- // Currently there is no mapping from the initiator user data to the source then
+ /**
+ * If the request to open a file originates from a direct token we might need to fetch the initiator user details when the initiator wopi token is accessed
+ * as the user might origin on a 3rd instance
+ */
+ if ($direct && !empty($direct->getInitiatorHost()) && !empty($direct->getInitiatorToken())) {
+ $this->tokenManager->extendWithInitiatorUserToken($wopi, $direct->getInitiatorHost(), $direct->getInitiatorToken());
}
$url = rtrim($remote, '/') . '/index.php/apps/richdocuments/remote?shareToken=' . $item->getStorage()->getToken() .
diff --git a/lib/TokenManager.php b/lib/TokenManager.php
index 4a7bebd7..90eb420a 100644
--- a/lib/TokenManager.php
+++ b/lib/TokenManager.php
@@ -225,9 +225,11 @@ class TokenManager {
$remoteTokenType = $remoteWopi->getEditorUid() !== null ? Wopi::TOKEN_TYPE_REMOTE_USER : Wopi::TOKEN_TYPE_REMOTE_GUEST;
$wopi->setTokenType($remoteTokenType);
- if ($remoteTokenType === Wopi::TOKEN_TYPE_REMOTE_USER) {
- $wopi->setGuestDisplayname($remoteWopi->getEditorUid() . '@' . $remoteServer);
- }
+ $wopi->setGuestDisplayname(
+ $remoteTokenType === Wopi::TOKEN_TYPE_REMOTE_USER ?
+ $remoteWopi->getEditorUid() . '@' . $remoteServer :
+ $remoteWopi->getGuestDisplayname()
+ );
$wopi->setShare($shareToken);
$wopi->setCanwrite($wopi->getCanwrite() && $remoteWopi->getCanwrite());
$wopi->setHideDownload($wopi->getHideDownload() || $remoteWopi->getHideDownload());
@@ -302,4 +304,11 @@ class TokenManager {
return $this->wopiMapper->generateInitiatorToken($this->userId, $sourceServer);
}
+ public function extendWithInitiatorUserToken(Wopi $wopi, string $initiatorUserHost, string $initiatorUserToken): Wopi {
+ $wopi->setRemoteServer($initiatorUserHost);
+ $wopi->setRemoteServerToken($initiatorUserToken);
+ $this->wopiMapper->update($wopi);
+ return $wopi;
+ }
+
}