Completed
Pull Request — master (#9345)
by Björn
16:57
created
apps/federatedfilesharing/lib/ocm/CloudFederationProviderFiles.php 1 patch
Indentation   +351 added lines, -351 removed lines patch added patch discarded remove patch
@@ -48,357 +48,357 @@
 block discarded – undo
48 48
 
49 49
 class CloudFederationProviderFiles implements ICloudFederationProvider {
50 50
 
51
-	/** @var IAppManager */
52
-	private $appManager;
53
-
54
-	/** @var FederatedShareProvider */
55
-	private $federatedShareProvider;
56
-
57
-	/** @var AddressHandler */
58
-	private $addressHandler;
59
-
60
-	/** @var ILogger */
61
-	private $logger;
62
-
63
-	/** @var IUserManager */
64
-	private $userManager;
65
-
66
-	/** @var ICloudIdManager */
67
-	private $cloudIdManager;
68
-
69
-	/** @var IActivityManager */
70
-	private $activityManager;
71
-
72
-	/** @var INotificationManager */
73
-	private $notificationManager;
74
-
75
-	/** @var IURLGenerator */
76
-	private $urlGenerator;
77
-
78
-	/**
79
-	 * CloudFederationProvider constructor.
80
-	 *
81
-	 * @param IAppManager $appManager
82
-	 * @param FederatedShareProvider $federatedShareProvider
83
-	 * @param AddressHandler $addressHandler
84
-	 * @param ILogger $logger
85
-	 * @param IUserManager $userManager
86
-	 * @param ICloudIdManager $cloudIdManager
87
-	 * @param IActivityManager $activityManager
88
-	 * @param INotificationManager $notificationManager
89
-	 * @param IURLGenerator $urlGenerator
90
-	 */
91
-	public function __construct(IAppManager $appManager,
92
-								FederatedShareProvider $federatedShareProvider,
93
-								AddressHandler $addressHandler,
94
-								ILogger $logger,
95
-								IUserManager $userManager,
96
-								ICloudIdManager $cloudIdManager,
97
-								IActivityManager $activityManager,
98
-								INotificationManager $notificationManager,
99
-								IURLGenerator $urlGenerator
100
-	) {
101
-		$this->appManager = $appManager;
102
-		$this->federatedShareProvider = $federatedShareProvider;
103
-		$this->addressHandler = $addressHandler;
104
-		$this->logger = $logger;
105
-		$this->userManager = $userManager;
106
-		$this->cloudIdManager = $cloudIdManager;
107
-		$this->activityManager = $activityManager;
108
-		$this->notificationManager = $notificationManager;
109
-		$this->urlGenerator = $urlGenerator;
110
-	}
111
-
112
-
113
-
114
-	/**
115
-	 * @return string
116
-	 */
117
-	public function getShareType() {
118
-		return 'file';
119
-	}
120
-
121
-	/**
122
-	 * share received from another server
123
-	 *
124
-	 * @param ICloudFederationShare $share
125
-	 * @return string provider specific unique ID of the share
126
-	 *
127
-	 * @throws ProviderCouldNotAddShareException
128
-	 * @throws \OCP\AppFramework\QueryException
129
-	 * @throws \OC\HintException
130
-	 * @since 14.0.0
131
-	 */
132
-	public function shareReceived(ICloudFederationShare $share) {
133
-
134
-		if (!$this->isS2SEnabled(true)) {
135
-			throw new ProviderCouldNotAddShareException('Server does not support federated cloud sharing', '', Http::STATUS_SERVICE_UNAVAILABLE);
136
-		}
137
-
138
-		$protocol = $share->getProtocol();
139
-		if ($protocol['name'] !== 'webdav') {
140
-			throw new ProviderCouldNotAddShareException('Unsupported protocol for data exchange.', '', Http::STATUS_NOT_IMPLEMENTED);
141
-		}
142
-
143
-		list($ownerUid, $remote) = $this->addressHandler->splitUserRemote($share->getOwner());
144
-
145
-		$remote = $remote;
146
-		$token = $share->getShareSecret();
147
-		$name = $share->getResourceName();
148
-		$owner = $share->getOwnerDisplayName();
149
-		$sharedBy = $share->getSharedByDisplayName();
150
-		$shareWith = $share->getShareWith();
151
-		$remoteId = $share->getProviderId();
152
-		$sharedByFederatedId = $share->getSharedBy();
153
-		$ownerFederatedId = $share->getOwner();
154
-
155
-		// if no explicit information about the person who created the share was send
156
-		// we assume that the share comes from the owner
157
-		if ($sharedByFederatedId === null) {
158
-			$sharedBy = $owner;
159
-			$sharedByFederatedId = $ownerFederatedId;
160
-		}
161
-
162
-		if ($remote && $token && $name && $owner && $remoteId && $shareWith) {
163
-
164
-			if (!Util::isValidFileName($name)) {
165
-				throw new ProviderCouldNotAddShareException('The mountpoint name contains invalid characters.', '', Http::STATUS_BAD_REQUEST);
166
-			}
167
-
168
-			// FIXME this should be a method in the user management instead
169
-			$this->logger->debug('shareWith before, ' . $shareWith, ['app' => 'files_sharing']);
170
-			Util::emitHook(
171
-				'\OCA\Files_Sharing\API\Server2Server',
172
-				'preLoginNameUsedAsUserName',
173
-				array('uid' => &$shareWith)
174
-			);
175
-			$this->logger->debug('shareWith after, ' . $shareWith, ['app' => 'files_sharing']);
176
-
177
-			if (!$this->userManager->userExists($shareWith)) {
178
-				throw new ProviderCouldNotAddShareException('User does not exists', '',Http::STATUS_BAD_REQUEST);
179
-			}
180
-
181
-			\OC_Util::setupFS($shareWith);
182
-
183
-			$externalManager = new \OCA\Files_Sharing\External\Manager(
184
-				\OC::$server->getDatabaseConnection(),
185
-				Filesystem::getMountManager(),
186
-				Filesystem::getLoader(),
187
-				\OC::$server->getHTTPClientService(),
188
-				\OC::$server->getNotificationManager(),
189
-				\OC::$server->query(\OCP\OCS\IDiscoveryService::class),
190
-				\OC::$server->getCloudFederationProviderManager(),
191
-				\OC::$server->getCloudFederationFactory(),
192
-				$shareWith
193
-			);
194
-
195
-			try {
196
-				$externalManager->addShare($remote, $token, '', $name, $owner, false, $shareWith, $remoteId);
197
-				$shareId = \OC::$server->getDatabaseConnection()->lastInsertId('*PREFIX*share_external');
198
-
199
-				$event = $this->activityManager->generateEvent();
200
-				$event->setApp('files_sharing')
201
-					->setType('remote_share')
202
-					->setSubject(RemoteShares::SUBJECT_REMOTE_SHARE_RECEIVED, [$ownerFederatedId, trim($name, '/')])
203
-					->setAffectedUser($shareWith)
204
-					->setObject('remote_share', (int)$shareId, $name);
205
-				\OC::$server->getActivityManager()->publish($event);
206
-
207
-				$notification = $this->notificationManager->createNotification();
208
-				$notification->setApp('files_sharing')
209
-					->setUser($shareWith)
210
-					->setDateTime(new \DateTime())
211
-					->setObject('remote_share', $shareId)
212
-					->setSubject('remote_share', [$ownerFederatedId, $sharedByFederatedId, trim($name, '/')]);
213
-
214
-				$declineAction = $notification->createAction();
215
-				$declineAction->setLabel('decline')
216
-					->setLink($this->urlGenerator->getAbsoluteURL($this->urlGenerator->linkTo('', 'ocs/v2.php/apps/files_sharing/api/v1/remote_shares/pending/' . $shareId)), 'DELETE');
217
-				$notification->addAction($declineAction);
218
-
219
-				$acceptAction = $notification->createAction();
220
-				$acceptAction->setLabel('accept')
221
-					->setLink($this->urlGenerator->getAbsoluteURL($this->urlGenerator->linkTo('', 'ocs/v2.php/apps/files_sharing/api/v1/remote_shares/pending/' . $shareId)), 'POST');
222
-				$notification->addAction($acceptAction);
223
-
224
-				$this->notificationManager->notify($notification);
225
-
226
-				return $shareId;
227
-			} catch (\Exception $e) {
228
-				$this->logger->logException($e, [
229
-					'message' => 'Server can not add remote share.',
230
-					'level' => Util::ERROR,
231
-					'app' => 'files_sharing'
232
-				]);
233
-				throw new ProviderCouldNotAddShareException('internal server error, was not able to add share from ' . $remote, '', HTTP::STATUS_INTERNAL_SERVER_ERROR);
234
-			}
235
-		}
236
-
237
-		throw new ProviderCouldNotAddShareException('server can not add remote share, missing parameter', '', HTTP::STATUS_BAD_REQUEST);
238
-
239
-	}
240
-
241
-	/**
242
-	 * notification received from another server
243
-	 *
244
-	 * @param string $notificationType (e.g. SHARE_ACCEPTED)
245
-	 * @param string $providerId id of the share
246
-	 * @param array $notification payload of the notification
247
-	 *
248
-	 * @throws ActionNotSupportedException
249
-	 * @throws AuthenticationFailedException
250
-	 * @throws BadRequestException
251
-	 * @throws ShareNotFoundException
252
-	 * @throws \OC\HintException
253
-	 * @since 14.0.0
254
-	 */
255
-	public function notificationReceived($notificationType, $providerId, array $notification) {
256
-
257
-		switch ($notificationType) {
258
-			case 'SHARE_ACCEPTED':
259
-				$this->shareAccepted($providerId, $notification);
260
-				return;
261
-		}
262
-
263
-
264
-		throw new ActionNotSupportedException($notification);
265
-	}
266
-
267
-	/**
268
-	 * @param $id
269
-	 * @param $notification
270
-	 * @return bool
271
-	 * @throws ActionNotSupportedException
272
-	 * @throws AuthenticationFailedException
273
-	 * @throws BadRequestException
274
-	 * @throws ShareNotFoundException
275
-	 * @throws \OC\HintException
276
-	 */
277
-	private function shareAccepted($id, $notification) {
278
-
279
-		if (!$this->isS2SEnabled(true)) {
280
-			throw new ActionNotSupportedException('Server does not support federated cloud sharing', '', Http::STATUS_SERVICE_UNAVAILABLE);
281
-		}
282
-
283
-		if (!isset($notification['sharedSecret'])) {
284
-			throw new BadRequestException(['sharedSecret']);
285
-		}
286
-
287
-		$token = $notification['sharedSecret'];
288
-
289
-		$share = $this->federatedShareProvider->getShareById($id);
290
-
291
-		$this->verifyShare($share, $token);
292
-		$this->executeAcceptShare($share);
293
-		if ($share->getShareOwner() !== $share->getSharedBy()) {
294
-			list(, $remote) = $this->addressHandler->splitUserRemote($share->getSharedBy());
295
-			$remoteId = $this->federatedShareProvider->getRemoteId($share);
296
-			$this->notifications->sendAcceptShare($remote, $remoteId, $share->getToken());
297
-		}
298
-
299
-		return true;
300
-	}
301
-
302
-
303
-	/**
304
-	 * @param IShare $share
305
-	 * @throws ShareNotFoundException
306
-	 */
307
-	protected function executeAcceptShare(IShare $share) {
308
-		try {
309
-			$fileId = (int)$share->getNode()->getId();
310
-			list($file, $link) = $this->getFile($this->getCorrectUid($share), $fileId);
311
-		} catch (\Exception $e) {
312
-			throw new ShareNotFoundException();
313
-		}
314
-
315
-		$event = $this->activityManager->generateEvent();
316
-		$event->setApp('files_sharing')
317
-			->setType('remote_share')
318
-			->setAffectedUser($this->getCorrectUid($share))
319
-			->setSubject(RemoteShares::SUBJECT_REMOTE_SHARE_ACCEPTED, [$share->getSharedWith(), [$fileId => $file]])
320
-			->setObject('files', $fileId, $file)
321
-			->setLink($link);
322
-		$this->activityManager->publish($event);
323
-	}
324
-
325
-	/**
326
-	 * get file
327
-	 *
328
-	 * @param string $user
329
-	 * @param int $fileSource
330
-	 * @return array with internal path of the file and a absolute link to it
331
-	 */
332
-	private function getFile($user, $fileSource) {
333
-		\OC_Util::setupFS($user);
334
-
335
-		try {
336
-			$file = Filesystem::getPath($fileSource);
337
-		} catch (NotFoundException $e) {
338
-			$file = null;
339
-		}
340
-		$args = Filesystem::is_dir($file) ? array('dir' => $file) : array('dir' => dirname($file), 'scrollto' => $file);
341
-		$link = Util::linkToAbsolute('files', 'index.php', $args);
342
-
343
-		return array($file, $link);
344
-
345
-	}
346
-
347
-	/**
348
-	 * check if we are the initiator or the owner of a re-share and return the correct UID
349
-	 *
350
-	 * @param IShare $share
351
-	 * @return string
352
-	 */
353
-	protected function getCorrectUid(IShare $share) {
354
-		if ($this->userManager->userExists($share->getShareOwner())) {
355
-			return $share->getShareOwner();
356
-		}
357
-
358
-		return $share->getSharedBy();
359
-	}
360
-
361
-
362
-
363
-	/**
364
-	 * check if we got the right share
365
-	 *
366
-	 * @param IShare $share
367
-	 * @param string $token
368
-	 * @return bool
369
-	 * @throws AuthenticationFailedException
370
-	 */
371
-	protected function verifyShare(IShare $share, $token) {
372
-		if (
373
-			$share->getShareType() === FederatedShareProvider::SHARE_TYPE_REMOTE &&
374
-			$share->getToken() === $token
375
-		) {
376
-			return true;
377
-		}
378
-
379
-		throw new AuthenticationFailedException();
380
-	}
381
-
382
-
383
-
384
-	/**
385
-	 * check if server-to-server sharing is enabled
386
-	 *
387
-	 * @param bool $incoming
388
-	 * @return bool
389
-	 */
390
-	private function isS2SEnabled($incoming = false) {
391
-
392
-		$result = $this->appManager->isEnabledForUser('files_sharing');
393
-
394
-		if ($incoming) {
395
-			$result = $result && $this->federatedShareProvider->isIncomingServer2serverShareEnabled();
396
-		} else {
397
-			$result = $result && $this->federatedShareProvider->isOutgoingServer2serverShareEnabled();
398
-		}
399
-
400
-		return $result;
401
-	}
51
+    /** @var IAppManager */
52
+    private $appManager;
53
+
54
+    /** @var FederatedShareProvider */
55
+    private $federatedShareProvider;
56
+
57
+    /** @var AddressHandler */
58
+    private $addressHandler;
59
+
60
+    /** @var ILogger */
61
+    private $logger;
62
+
63
+    /** @var IUserManager */
64
+    private $userManager;
65
+
66
+    /** @var ICloudIdManager */
67
+    private $cloudIdManager;
68
+
69
+    /** @var IActivityManager */
70
+    private $activityManager;
71
+
72
+    /** @var INotificationManager */
73
+    private $notificationManager;
74
+
75
+    /** @var IURLGenerator */
76
+    private $urlGenerator;
77
+
78
+    /**
79
+     * CloudFederationProvider constructor.
80
+     *
81
+     * @param IAppManager $appManager
82
+     * @param FederatedShareProvider $federatedShareProvider
83
+     * @param AddressHandler $addressHandler
84
+     * @param ILogger $logger
85
+     * @param IUserManager $userManager
86
+     * @param ICloudIdManager $cloudIdManager
87
+     * @param IActivityManager $activityManager
88
+     * @param INotificationManager $notificationManager
89
+     * @param IURLGenerator $urlGenerator
90
+     */
91
+    public function __construct(IAppManager $appManager,
92
+                                FederatedShareProvider $federatedShareProvider,
93
+                                AddressHandler $addressHandler,
94
+                                ILogger $logger,
95
+                                IUserManager $userManager,
96
+                                ICloudIdManager $cloudIdManager,
97
+                                IActivityManager $activityManager,
98
+                                INotificationManager $notificationManager,
99
+                                IURLGenerator $urlGenerator
100
+    ) {
101
+        $this->appManager = $appManager;
102
+        $this->federatedShareProvider = $federatedShareProvider;
103
+        $this->addressHandler = $addressHandler;
104
+        $this->logger = $logger;
105
+        $this->userManager = $userManager;
106
+        $this->cloudIdManager = $cloudIdManager;
107
+        $this->activityManager = $activityManager;
108
+        $this->notificationManager = $notificationManager;
109
+        $this->urlGenerator = $urlGenerator;
110
+    }
111
+
112
+
113
+
114
+    /**
115
+     * @return string
116
+     */
117
+    public function getShareType() {
118
+        return 'file';
119
+    }
120
+
121
+    /**
122
+     * share received from another server
123
+     *
124
+     * @param ICloudFederationShare $share
125
+     * @return string provider specific unique ID of the share
126
+     *
127
+     * @throws ProviderCouldNotAddShareException
128
+     * @throws \OCP\AppFramework\QueryException
129
+     * @throws \OC\HintException
130
+     * @since 14.0.0
131
+     */
132
+    public function shareReceived(ICloudFederationShare $share) {
133
+
134
+        if (!$this->isS2SEnabled(true)) {
135
+            throw new ProviderCouldNotAddShareException('Server does not support federated cloud sharing', '', Http::STATUS_SERVICE_UNAVAILABLE);
136
+        }
137
+
138
+        $protocol = $share->getProtocol();
139
+        if ($protocol['name'] !== 'webdav') {
140
+            throw new ProviderCouldNotAddShareException('Unsupported protocol for data exchange.', '', Http::STATUS_NOT_IMPLEMENTED);
141
+        }
142
+
143
+        list($ownerUid, $remote) = $this->addressHandler->splitUserRemote($share->getOwner());
144
+
145
+        $remote = $remote;
146
+        $token = $share->getShareSecret();
147
+        $name = $share->getResourceName();
148
+        $owner = $share->getOwnerDisplayName();
149
+        $sharedBy = $share->getSharedByDisplayName();
150
+        $shareWith = $share->getShareWith();
151
+        $remoteId = $share->getProviderId();
152
+        $sharedByFederatedId = $share->getSharedBy();
153
+        $ownerFederatedId = $share->getOwner();
154
+
155
+        // if no explicit information about the person who created the share was send
156
+        // we assume that the share comes from the owner
157
+        if ($sharedByFederatedId === null) {
158
+            $sharedBy = $owner;
159
+            $sharedByFederatedId = $ownerFederatedId;
160
+        }
161
+
162
+        if ($remote && $token && $name && $owner && $remoteId && $shareWith) {
163
+
164
+            if (!Util::isValidFileName($name)) {
165
+                throw new ProviderCouldNotAddShareException('The mountpoint name contains invalid characters.', '', Http::STATUS_BAD_REQUEST);
166
+            }
167
+
168
+            // FIXME this should be a method in the user management instead
169
+            $this->logger->debug('shareWith before, ' . $shareWith, ['app' => 'files_sharing']);
170
+            Util::emitHook(
171
+                '\OCA\Files_Sharing\API\Server2Server',
172
+                'preLoginNameUsedAsUserName',
173
+                array('uid' => &$shareWith)
174
+            );
175
+            $this->logger->debug('shareWith after, ' . $shareWith, ['app' => 'files_sharing']);
176
+
177
+            if (!$this->userManager->userExists($shareWith)) {
178
+                throw new ProviderCouldNotAddShareException('User does not exists', '',Http::STATUS_BAD_REQUEST);
179
+            }
180
+
181
+            \OC_Util::setupFS($shareWith);
182
+
183
+            $externalManager = new \OCA\Files_Sharing\External\Manager(
184
+                \OC::$server->getDatabaseConnection(),
185
+                Filesystem::getMountManager(),
186
+                Filesystem::getLoader(),
187
+                \OC::$server->getHTTPClientService(),
188
+                \OC::$server->getNotificationManager(),
189
+                \OC::$server->query(\OCP\OCS\IDiscoveryService::class),
190
+                \OC::$server->getCloudFederationProviderManager(),
191
+                \OC::$server->getCloudFederationFactory(),
192
+                $shareWith
193
+            );
194
+
195
+            try {
196
+                $externalManager->addShare($remote, $token, '', $name, $owner, false, $shareWith, $remoteId);
197
+                $shareId = \OC::$server->getDatabaseConnection()->lastInsertId('*PREFIX*share_external');
198
+
199
+                $event = $this->activityManager->generateEvent();
200
+                $event->setApp('files_sharing')
201
+                    ->setType('remote_share')
202
+                    ->setSubject(RemoteShares::SUBJECT_REMOTE_SHARE_RECEIVED, [$ownerFederatedId, trim($name, '/')])
203
+                    ->setAffectedUser($shareWith)
204
+                    ->setObject('remote_share', (int)$shareId, $name);
205
+                \OC::$server->getActivityManager()->publish($event);
206
+
207
+                $notification = $this->notificationManager->createNotification();
208
+                $notification->setApp('files_sharing')
209
+                    ->setUser($shareWith)
210
+                    ->setDateTime(new \DateTime())
211
+                    ->setObject('remote_share', $shareId)
212
+                    ->setSubject('remote_share', [$ownerFederatedId, $sharedByFederatedId, trim($name, '/')]);
213
+
214
+                $declineAction = $notification->createAction();
215
+                $declineAction->setLabel('decline')
216
+                    ->setLink($this->urlGenerator->getAbsoluteURL($this->urlGenerator->linkTo('', 'ocs/v2.php/apps/files_sharing/api/v1/remote_shares/pending/' . $shareId)), 'DELETE');
217
+                $notification->addAction($declineAction);
218
+
219
+                $acceptAction = $notification->createAction();
220
+                $acceptAction->setLabel('accept')
221
+                    ->setLink($this->urlGenerator->getAbsoluteURL($this->urlGenerator->linkTo('', 'ocs/v2.php/apps/files_sharing/api/v1/remote_shares/pending/' . $shareId)), 'POST');
222
+                $notification->addAction($acceptAction);
223
+
224
+                $this->notificationManager->notify($notification);
225
+
226
+                return $shareId;
227
+            } catch (\Exception $e) {
228
+                $this->logger->logException($e, [
229
+                    'message' => 'Server can not add remote share.',
230
+                    'level' => Util::ERROR,
231
+                    'app' => 'files_sharing'
232
+                ]);
233
+                throw new ProviderCouldNotAddShareException('internal server error, was not able to add share from ' . $remote, '', HTTP::STATUS_INTERNAL_SERVER_ERROR);
234
+            }
235
+        }
236
+
237
+        throw new ProviderCouldNotAddShareException('server can not add remote share, missing parameter', '', HTTP::STATUS_BAD_REQUEST);
238
+
239
+    }
240
+
241
+    /**
242
+     * notification received from another server
243
+     *
244
+     * @param string $notificationType (e.g. SHARE_ACCEPTED)
245
+     * @param string $providerId id of the share
246
+     * @param array $notification payload of the notification
247
+     *
248
+     * @throws ActionNotSupportedException
249
+     * @throws AuthenticationFailedException
250
+     * @throws BadRequestException
251
+     * @throws ShareNotFoundException
252
+     * @throws \OC\HintException
253
+     * @since 14.0.0
254
+     */
255
+    public function notificationReceived($notificationType, $providerId, array $notification) {
256
+
257
+        switch ($notificationType) {
258
+            case 'SHARE_ACCEPTED':
259
+                $this->shareAccepted($providerId, $notification);
260
+                return;
261
+        }
262
+
263
+
264
+        throw new ActionNotSupportedException($notification);
265
+    }
266
+
267
+    /**
268
+     * @param $id
269
+     * @param $notification
270
+     * @return bool
271
+     * @throws ActionNotSupportedException
272
+     * @throws AuthenticationFailedException
273
+     * @throws BadRequestException
274
+     * @throws ShareNotFoundException
275
+     * @throws \OC\HintException
276
+     */
277
+    private function shareAccepted($id, $notification) {
278
+
279
+        if (!$this->isS2SEnabled(true)) {
280
+            throw new ActionNotSupportedException('Server does not support federated cloud sharing', '', Http::STATUS_SERVICE_UNAVAILABLE);
281
+        }
282
+
283
+        if (!isset($notification['sharedSecret'])) {
284
+            throw new BadRequestException(['sharedSecret']);
285
+        }
286
+
287
+        $token = $notification['sharedSecret'];
288
+
289
+        $share = $this->federatedShareProvider->getShareById($id);
290
+
291
+        $this->verifyShare($share, $token);
292
+        $this->executeAcceptShare($share);
293
+        if ($share->getShareOwner() !== $share->getSharedBy()) {
294
+            list(, $remote) = $this->addressHandler->splitUserRemote($share->getSharedBy());
295
+            $remoteId = $this->federatedShareProvider->getRemoteId($share);
296
+            $this->notifications->sendAcceptShare($remote, $remoteId, $share->getToken());
297
+        }
298
+
299
+        return true;
300
+    }
301
+
302
+
303
+    /**
304
+     * @param IShare $share
305
+     * @throws ShareNotFoundException
306
+     */
307
+    protected function executeAcceptShare(IShare $share) {
308
+        try {
309
+            $fileId = (int)$share->getNode()->getId();
310
+            list($file, $link) = $this->getFile($this->getCorrectUid($share), $fileId);
311
+        } catch (\Exception $e) {
312
+            throw new ShareNotFoundException();
313
+        }
314
+
315
+        $event = $this->activityManager->generateEvent();
316
+        $event->setApp('files_sharing')
317
+            ->setType('remote_share')
318
+            ->setAffectedUser($this->getCorrectUid($share))
319
+            ->setSubject(RemoteShares::SUBJECT_REMOTE_SHARE_ACCEPTED, [$share->getSharedWith(), [$fileId => $file]])
320
+            ->setObject('files', $fileId, $file)
321
+            ->setLink($link);
322
+        $this->activityManager->publish($event);
323
+    }
324
+
325
+    /**
326
+     * get file
327
+     *
328
+     * @param string $user
329
+     * @param int $fileSource
330
+     * @return array with internal path of the file and a absolute link to it
331
+     */
332
+    private function getFile($user, $fileSource) {
333
+        \OC_Util::setupFS($user);
334
+
335
+        try {
336
+            $file = Filesystem::getPath($fileSource);
337
+        } catch (NotFoundException $e) {
338
+            $file = null;
339
+        }
340
+        $args = Filesystem::is_dir($file) ? array('dir' => $file) : array('dir' => dirname($file), 'scrollto' => $file);
341
+        $link = Util::linkToAbsolute('files', 'index.php', $args);
342
+
343
+        return array($file, $link);
344
+
345
+    }
346
+
347
+    /**
348
+     * check if we are the initiator or the owner of a re-share and return the correct UID
349
+     *
350
+     * @param IShare $share
351
+     * @return string
352
+     */
353
+    protected function getCorrectUid(IShare $share) {
354
+        if ($this->userManager->userExists($share->getShareOwner())) {
355
+            return $share->getShareOwner();
356
+        }
357
+
358
+        return $share->getSharedBy();
359
+    }
360
+
361
+
362
+
363
+    /**
364
+     * check if we got the right share
365
+     *
366
+     * @param IShare $share
367
+     * @param string $token
368
+     * @return bool
369
+     * @throws AuthenticationFailedException
370
+     */
371
+    protected function verifyShare(IShare $share, $token) {
372
+        if (
373
+            $share->getShareType() === FederatedShareProvider::SHARE_TYPE_REMOTE &&
374
+            $share->getToken() === $token
375
+        ) {
376
+            return true;
377
+        }
378
+
379
+        throw new AuthenticationFailedException();
380
+    }
381
+
382
+
383
+
384
+    /**
385
+     * check if server-to-server sharing is enabled
386
+     *
387
+     * @param bool $incoming
388
+     * @return bool
389
+     */
390
+    private function isS2SEnabled($incoming = false) {
391
+
392
+        $result = $this->appManager->isEnabledForUser('files_sharing');
393
+
394
+        if ($incoming) {
395
+            $result = $result && $this->federatedShareProvider->isIncomingServer2serverShareEnabled();
396
+        } else {
397
+            $result = $result && $this->federatedShareProvider->isOutgoingServer2serverShareEnabled();
398
+        }
399
+
400
+        return $result;
401
+    }
402 402
 
403 403
 
404 404
 }
Please login to merge, or discard this patch.
apps/cloud_federation_api/lib/Capabilities.php 1 patch
Indentation   +30 added lines, -30 removed lines patch added patch discarded remove patch
@@ -28,37 +28,37 @@
 block discarded – undo
28 28
 
29 29
 class Capabilities implements ICapability {
30 30
 
31
-	/** @var IURLGenerator */
32
-	private $urlGenerator;
31
+    /** @var IURLGenerator */
32
+    private $urlGenerator;
33 33
 
34
-	public function __construct(IURLGenerator $urlGenerator) {
35
-		$this->urlGenerator = $urlGenerator;
36
-	}
34
+    public function __construct(IURLGenerator $urlGenerator) {
35
+        $this->urlGenerator = $urlGenerator;
36
+    }
37 37
 
38
-	/**
39
-	 * Function an app uses to return the capabilities
40
-	 *
41
-	 * @return array Array containing the apps capabilities
42
-	 * @since 8.2.0
43
-	 */
44
-	public function getCapabilities() {
45
-		$url = $this->urlGenerator->linkToRouteAbsolute('cloud_federation_api.requesthandlercontroller.addShare');
46
-		$capabilities = ['ocm' =>
47
-			[
48
-				'enabled' => true,
49
-				'apiVersion' => '1.0-proposal1',
50
-				'endPoint' => substr($url, 0, strrpos($url, '/')),
51
-				'shareTypes' => [
52
-					[
53
-						'name' => 'file',
54
-						'protocols' => [
55
-							'webdav' => '/public.php/webdav/',
56
-						]
57
-					],
58
-				]
59
-			]
60
-		];
38
+    /**
39
+     * Function an app uses to return the capabilities
40
+     *
41
+     * @return array Array containing the apps capabilities
42
+     * @since 8.2.0
43
+     */
44
+    public function getCapabilities() {
45
+        $url = $this->urlGenerator->linkToRouteAbsolute('cloud_federation_api.requesthandlercontroller.addShare');
46
+        $capabilities = ['ocm' =>
47
+            [
48
+                'enabled' => true,
49
+                'apiVersion' => '1.0-proposal1',
50
+                'endPoint' => substr($url, 0, strrpos($url, '/')),
51
+                'shareTypes' => [
52
+                    [
53
+                        'name' => 'file',
54
+                        'protocols' => [
55
+                            'webdav' => '/public.php/webdav/',
56
+                        ]
57
+                    ],
58
+                ]
59
+            ]
60
+        ];
61 61
 
62
-		return $capabilities;
63
-	}
62
+        return $capabilities;
63
+    }
64 64
 }
Please login to merge, or discard this patch.
apps/cloud_federation_api/lib/Controller/RequestHandlerController.php 1 patch
Indentation   +203 added lines, -203 removed lines patch added patch discarded remove patch
@@ -51,233 +51,233 @@
 block discarded – undo
51 51
  */
52 52
 class RequestHandlerController extends Controller {
53 53
 
54
-	/** @var ILogger */
55
-	private $logger;
54
+    /** @var ILogger */
55
+    private $logger;
56 56
 
57
-	/** @var IUserManager */
58
-	private $userManager;
57
+    /** @var IUserManager */
58
+    private $userManager;
59 59
 
60
-	/** @var IURLGenerator */
61
-	private $urlGenerator;
60
+    /** @var IURLGenerator */
61
+    private $urlGenerator;
62 62
 
63
-	/** @var ICloudFederationProviderManager */
64
-	private $cloudFederationProviderManager;
63
+    /** @var ICloudFederationProviderManager */
64
+    private $cloudFederationProviderManager;
65 65
 
66
-	/** @var Config */
67
-	private $config;
66
+    /** @var Config */
67
+    private $config;
68 68
 
69
-	/** @var ICloudFederationFactory */
70
-	private $factory;
69
+    /** @var ICloudFederationFactory */
70
+    private $factory;
71 71
 
72
-	/** @var ICloudIdManager */
73
-	private $cloudIdManager;
72
+    /** @var ICloudIdManager */
73
+    private $cloudIdManager;
74 74
 
75
-	public function __construct($appName,
76
-								IRequest $request,
77
-								ILogger $logger,
78
-								IUserManager $userManager,
79
-								IURLGenerator $urlGenerator,
80
-								ICloudFederationProviderManager $cloudFederationProviderManager,
81
-								Config $config,
82
-								ICloudFederationFactory $factory,
83
-								ICloudIdManager $cloudIdManager
84
-	) {
85
-		parent::__construct($appName, $request);
75
+    public function __construct($appName,
76
+                                IRequest $request,
77
+                                ILogger $logger,
78
+                                IUserManager $userManager,
79
+                                IURLGenerator $urlGenerator,
80
+                                ICloudFederationProviderManager $cloudFederationProviderManager,
81
+                                Config $config,
82
+                                ICloudFederationFactory $factory,
83
+                                ICloudIdManager $cloudIdManager
84
+    ) {
85
+        parent::__construct($appName, $request);
86 86
 
87
-		$this->logger = $logger;
88
-		$this->userManager = $userManager;
89
-		$this->urlGenerator = $urlGenerator;
90
-		$this->cloudFederationProviderManager = $cloudFederationProviderManager;
91
-		$this->config = $config;
92
-		$this->factory = $factory;
93
-		$this->cloudIdManager = $cloudIdManager;
94
-	}
87
+        $this->logger = $logger;
88
+        $this->userManager = $userManager;
89
+        $this->urlGenerator = $urlGenerator;
90
+        $this->cloudFederationProviderManager = $cloudFederationProviderManager;
91
+        $this->config = $config;
92
+        $this->factory = $factory;
93
+        $this->cloudIdManager = $cloudIdManager;
94
+    }
95 95
 
96
-	/**
97
-	 * add share
98
-	 *
99
-	 * @NoCSRFRequired
100
-	 * @PublicPage
101
-	 * @BruteForceProtection(action=receiveFederatedShare)
102
-	 *
103
-	 * @param string $shareWith
104
-	 * @param string $name resource name (e.g. document.odt)
105
-	 * @param string $description share description (optional)
106
-	 * @param string $providerId resource UID on the provider side
107
-	 * @param string $owner provider specific UID of the user who owns the resource
108
-	 * @param string $ownerDisplayName display name of the user who shared the item
109
-	 * @param string $sharedBy provider specific UID of the user who shared the resource
110
-	 * @param string $sharedByDisplayName display name of the user who shared the resource
111
-	 * @param string $sharedSecret use to authenticate accross servers
112
-	 * @param array $protocol (e,.g. ['name' => 'webdav', 'options' => ['username' => 'john', 'permissions' => 31]])
113
-	 * @param string $shareType ('group' or 'user' share)
114
-	 * @param $resourceType ('file', 'calendar',...)
115
-	 * @return Http\DataResponse|JSONResponse
116
-	 *
117
-	 * Example: curl -H "Content-Type: application/json" -X POST -d '{"shareWith":"admin1@serve1","name":"welcome server2.txt","description":"desc","providerId":"2","owner":"admin2@http://localhost/server2","ownerDisplayName":"admin2 display","shareType":"user","resourceType":"file","protocol":{"name":"webdav","options":{"sharedSecret":"secret","permissions":"webdav-property"}}}' http://localhost/server/index.php/ocm/shares
118
-	 */
119
-	public function addShare($shareWith, $name, $description, $providerId, $owner, $ownerDisplayName, $sharedBy, $sharedByDisplayName, $protocol, $shareType, $resourceType) {
120
-		if (!$this->config->incomingRequestsEnabled()) {
121
-			return new JSONResponse(
122
-				['message' => 'This server doesn\'t support outgoing federated shares'],
123
-			Http::STATUS_NOT_IMPLEMENTED
124
-			);
125
-		}
96
+    /**
97
+     * add share
98
+     *
99
+     * @NoCSRFRequired
100
+     * @PublicPage
101
+     * @BruteForceProtection(action=receiveFederatedShare)
102
+     *
103
+     * @param string $shareWith
104
+     * @param string $name resource name (e.g. document.odt)
105
+     * @param string $description share description (optional)
106
+     * @param string $providerId resource UID on the provider side
107
+     * @param string $owner provider specific UID of the user who owns the resource
108
+     * @param string $ownerDisplayName display name of the user who shared the item
109
+     * @param string $sharedBy provider specific UID of the user who shared the resource
110
+     * @param string $sharedByDisplayName display name of the user who shared the resource
111
+     * @param string $sharedSecret use to authenticate accross servers
112
+     * @param array $protocol (e,.g. ['name' => 'webdav', 'options' => ['username' => 'john', 'permissions' => 31]])
113
+     * @param string $shareType ('group' or 'user' share)
114
+     * @param $resourceType ('file', 'calendar',...)
115
+     * @return Http\DataResponse|JSONResponse
116
+     *
117
+     * Example: curl -H "Content-Type: application/json" -X POST -d '{"shareWith":"admin1@serve1","name":"welcome server2.txt","description":"desc","providerId":"2","owner":"admin2@http://localhost/server2","ownerDisplayName":"admin2 display","shareType":"user","resourceType":"file","protocol":{"name":"webdav","options":{"sharedSecret":"secret","permissions":"webdav-property"}}}' http://localhost/server/index.php/ocm/shares
118
+     */
119
+    public function addShare($shareWith, $name, $description, $providerId, $owner, $ownerDisplayName, $sharedBy, $sharedByDisplayName, $protocol, $shareType, $resourceType) {
120
+        if (!$this->config->incomingRequestsEnabled()) {
121
+            return new JSONResponse(
122
+                ['message' => 'This server doesn\'t support outgoing federated shares'],
123
+            Http::STATUS_NOT_IMPLEMENTED
124
+            );
125
+        }
126 126
 
127
-		// check if all required parameters are set
128
-		if ($shareWith === null ||
129
-			$name === null ||
130
-			$providerId === null ||
131
-			$owner === null ||
132
-			$resourceType === null ||
133
-			$shareType === null ||
134
-			!is_array($protocol) ||
135
-			!isset($protocol['name']) ||
136
-			!isset ($protocol['options']) ||
137
-			!is_array($protocol['options']) ||
138
-			!isset($protocol['options']['sharedSecret'])
139
-		) {
140
-			return new JSONResponse(
141
-				['message' => 'Missing arguments'],
142
-				Http::STATUS_BAD_REQUEST
143
-			);
144
-		}
127
+        // check if all required parameters are set
128
+        if ($shareWith === null ||
129
+            $name === null ||
130
+            $providerId === null ||
131
+            $owner === null ||
132
+            $resourceType === null ||
133
+            $shareType === null ||
134
+            !is_array($protocol) ||
135
+            !isset($protocol['name']) ||
136
+            !isset ($protocol['options']) ||
137
+            !is_array($protocol['options']) ||
138
+            !isset($protocol['options']['sharedSecret'])
139
+        ) {
140
+            return new JSONResponse(
141
+                ['message' => 'Missing arguments'],
142
+                Http::STATUS_BAD_REQUEST
143
+            );
144
+        }
145 145
 
146
-		$cloudId = $this->cloudIdManager->resolveCloudId($shareWith);
147
-		$shareWithLocalId = $cloudId->getUser();
148
-		$shareWith = $this->mapUid($shareWithLocalId);
146
+        $cloudId = $this->cloudIdManager->resolveCloudId($shareWith);
147
+        $shareWithLocalId = $cloudId->getUser();
148
+        $shareWith = $this->mapUid($shareWithLocalId);
149 149
 
150
-		if (!$this->userManager->userExists($shareWith)) {
151
-			return new JSONResponse(
152
-				['message' => 'User "' . $shareWith . '" does not exists at ' . $this->urlGenerator->getBaseUrl()],
153
-				Http::STATUS_BAD_REQUEST
154
-			);
155
-		}
150
+        if (!$this->userManager->userExists($shareWith)) {
151
+            return new JSONResponse(
152
+                ['message' => 'User "' . $shareWith . '" does not exists at ' . $this->urlGenerator->getBaseUrl()],
153
+                Http::STATUS_BAD_REQUEST
154
+            );
155
+        }
156 156
 
157
-		// if no explicit display name is given, we use the uid as display name
158
-		$ownerDisplayName = $ownerDisplayName === null ? $owner : $ownerDisplayName;
159
-		$sharedByDisplayName = $sharedByDisplayName === null ? $sharedBy : $sharedByDisplayName;
157
+        // if no explicit display name is given, we use the uid as display name
158
+        $ownerDisplayName = $ownerDisplayName === null ? $owner : $ownerDisplayName;
159
+        $sharedByDisplayName = $sharedByDisplayName === null ? $sharedBy : $sharedByDisplayName;
160 160
 
161
-		// sharedBy* parameter is optional, if nothing is set we assume that it is the same user as the owner
162
-		if ($sharedBy === null) {
163
-			$sharedBy = $owner;
164
-			$sharedByDisplayName = $ownerDisplayName;
165
-		}
161
+        // sharedBy* parameter is optional, if nothing is set we assume that it is the same user as the owner
162
+        if ($sharedBy === null) {
163
+            $sharedBy = $owner;
164
+            $sharedByDisplayName = $ownerDisplayName;
165
+        }
166 166
 
167
-		try {
168
-			$provider = $this->cloudFederationProviderManager->getCloudFederationProvider($resourceType);
169
-			$share = $this->factory->getCloudFederationShare($shareWith, $name, $description, $providerId, $owner, $ownerDisplayName, $sharedBy, $sharedByDisplayName, '', $shareType, $resourceType);
170
-			$share->setProtocol($protocol);
171
-			$id = $provider->shareReceived($share);
172
-		} catch (ProviderDoesNotExistsException $e) {
173
-			return new JSONResponse(
174
-				['message' => $e->getMessage()],
175
-				Http::STATUS_NOT_IMPLEMENTED
176
-			);
177
-		} catch (ProviderCouldNotAddShareException $e) {
178
-			return new JSONResponse(
179
-				['message' => $e->getMessage()],
180
-				$e->getCode()
181
-			);
182
-		} catch (\Exception $e) {
183
-			return new JSONResponse(
184
-				['message' => 'Internal error at ' . $this->urlGenerator->getBaseUrl()],
185
-				Http::STATUS_BAD_REQUEST
186
-			);
187
-		}
167
+        try {
168
+            $provider = $this->cloudFederationProviderManager->getCloudFederationProvider($resourceType);
169
+            $share = $this->factory->getCloudFederationShare($shareWith, $name, $description, $providerId, $owner, $ownerDisplayName, $sharedBy, $sharedByDisplayName, '', $shareType, $resourceType);
170
+            $share->setProtocol($protocol);
171
+            $id = $provider->shareReceived($share);
172
+        } catch (ProviderDoesNotExistsException $e) {
173
+            return new JSONResponse(
174
+                ['message' => $e->getMessage()],
175
+                Http::STATUS_NOT_IMPLEMENTED
176
+            );
177
+        } catch (ProviderCouldNotAddShareException $e) {
178
+            return new JSONResponse(
179
+                ['message' => $e->getMessage()],
180
+                $e->getCode()
181
+            );
182
+        } catch (\Exception $e) {
183
+            return new JSONResponse(
184
+                ['message' => 'Internal error at ' . $this->urlGenerator->getBaseUrl()],
185
+                Http::STATUS_BAD_REQUEST
186
+            );
187
+        }
188 188
 
189
-		return new JSONResponse(
190
-			['id' => $id, 'createdAt' => time()],
191
-			Http::STATUS_CREATED);
189
+        return new JSONResponse(
190
+            ['id' => $id, 'createdAt' => time()],
191
+            Http::STATUS_CREATED);
192 192
 
193
-	}
193
+    }
194 194
 
195
-	/**
196
-	 * receive notification about existing share
197
-	 *
198
-	 * @NoCSRFRequired
199
-	 * @PublicPage
200
-	 * @BruteForceProtection(action=receiveFederatedShareNotification)
201
-	 *
202
-	 * @param string $notificationType (notification type, e.g. SHARE_ACCEPTED)
203
-	 * @param string $resourceType (calendar, file, contact,...)
204
-	 * @param string $providerId id of the share
205
-	 * @param array $notification the actual payload of the notification
206
-	 * @return JSONResponse
207
-	 */
208
-	public function receiveNotification($notificationType, $resourceType, $providerId, array $notification) {
209
-		if (!$this->config->incomingRequestsEnabled()) {
210
-			return new JSONResponse(
211
-				['message' => 'This server doesn\'t support outgoing federated shares'],
212
-				Http::STATUS_NOT_IMPLEMENTED
213
-			);
214
-		}
195
+    /**
196
+     * receive notification about existing share
197
+     *
198
+     * @NoCSRFRequired
199
+     * @PublicPage
200
+     * @BruteForceProtection(action=receiveFederatedShareNotification)
201
+     *
202
+     * @param string $notificationType (notification type, e.g. SHARE_ACCEPTED)
203
+     * @param string $resourceType (calendar, file, contact,...)
204
+     * @param string $providerId id of the share
205
+     * @param array $notification the actual payload of the notification
206
+     * @return JSONResponse
207
+     */
208
+    public function receiveNotification($notificationType, $resourceType, $providerId, array $notification) {
209
+        if (!$this->config->incomingRequestsEnabled()) {
210
+            return new JSONResponse(
211
+                ['message' => 'This server doesn\'t support outgoing federated shares'],
212
+                Http::STATUS_NOT_IMPLEMENTED
213
+            );
214
+        }
215 215
 
216
-		// check if all required parameters are set
217
-		if ($notificationType === null ||
218
-			$resourceType === null ||
219
-			$providerId === null ||
220
-			!is_array($notification)
221
-		) {
222
-			return new JSONResponse(
223
-				['message' => 'Missing arguments'],
224
-				Http::STATUS_BAD_REQUEST
225
-			);
226
-		}
216
+        // check if all required parameters are set
217
+        if ($notificationType === null ||
218
+            $resourceType === null ||
219
+            $providerId === null ||
220
+            !is_array($notification)
221
+        ) {
222
+            return new JSONResponse(
223
+                ['message' => 'Missing arguments'],
224
+                Http::STATUS_BAD_REQUEST
225
+            );
226
+        }
227 227
 
228
-		try {
229
-			$provider = $this->cloudFederationProviderManager->getCloudFederationProvider($resourceType);
230
-			$provider->notificationReceived($notificationType, $providerId, $notification);
231
-		} catch (ProviderDoesNotExistsException $e) {
232
-			return new JSONResponse(
233
-				['message' => $e->getMessage()],
234
-				Http::STATUS_BAD_REQUEST
235
-			);
236
-		} catch (ShareNotFoundException $e) {
237
-			return new JSONResponse(
238
-				['message' => $e->getMessage()],
239
-				Http::STATUS_BAD_REQUEST
240
-			);
241
-		} catch (ActionNotSupportedException $e) {
242
-			return new JSONResponse(
243
-				['message' => $e->getMessage()],
244
-				Http::STATUS_NOT_IMPLEMENTED
245
-			);
246
-		} catch (BadRequestException $e) {
247
-			return new JSONResponse($e->getReturnMessage(), Http::STATUS_BAD_REQUEST);
248
-		} catch (AuthenticationFailedException $e) {
249
-			return new JSONResponse(["message" => "RESOURCE_NOT_FOUND"], Http::STATUS_FORBIDDEN);
250
-		}
251
-		catch (\Exception $e) {
252
-			return new JSONResponse(
253
-				['message' => 'Internal error at ' . $this->urlGenerator->getBaseUrl()],
254
-				Http::STATUS_BAD_REQUEST
255
-			);
256
-		}
228
+        try {
229
+            $provider = $this->cloudFederationProviderManager->getCloudFederationProvider($resourceType);
230
+            $provider->notificationReceived($notificationType, $providerId, $notification);
231
+        } catch (ProviderDoesNotExistsException $e) {
232
+            return new JSONResponse(
233
+                ['message' => $e->getMessage()],
234
+                Http::STATUS_BAD_REQUEST
235
+            );
236
+        } catch (ShareNotFoundException $e) {
237
+            return new JSONResponse(
238
+                ['message' => $e->getMessage()],
239
+                Http::STATUS_BAD_REQUEST
240
+            );
241
+        } catch (ActionNotSupportedException $e) {
242
+            return new JSONResponse(
243
+                ['message' => $e->getMessage()],
244
+                Http::STATUS_NOT_IMPLEMENTED
245
+            );
246
+        } catch (BadRequestException $e) {
247
+            return new JSONResponse($e->getReturnMessage(), Http::STATUS_BAD_REQUEST);
248
+        } catch (AuthenticationFailedException $e) {
249
+            return new JSONResponse(["message" => "RESOURCE_NOT_FOUND"], Http::STATUS_FORBIDDEN);
250
+        }
251
+        catch (\Exception $e) {
252
+            return new JSONResponse(
253
+                ['message' => 'Internal error at ' . $this->urlGenerator->getBaseUrl()],
254
+                Http::STATUS_BAD_REQUEST
255
+            );
256
+        }
257 257
 
258 258
 
259
-		return new JSONResponse([],Http::STATUS_CREATED);
259
+        return new JSONResponse([],Http::STATUS_CREATED);
260 260
 
261
-	}
261
+    }
262 262
 
263
-	/**
264
-	 * map login name to internal LDAP UID if a LDAP backend is in use
265
-	 *
266
-	 * @param string $uid
267
-	 * @return string mixed
268
-	 */
269
-	private function mapUid($uid) {
270
-		\OC::$server->getURLGenerator()->linkToDocs('key');
271
-		// FIXME this should be a method in the user management instead
272
-		$this->logger->debug('shareWith before, ' . $uid, ['app' => $this->appName]);
273
-		\OCP\Util::emitHook(
274
-			'\OCA\Files_Sharing\API\Server2Server',
275
-			'preLoginNameUsedAsUserName',
276
-			array('uid' => &$uid)
277
-		);
278
-		$this->logger->debug('shareWith after, ' . $uid, ['app' => $this->appName]);
263
+    /**
264
+     * map login name to internal LDAP UID if a LDAP backend is in use
265
+     *
266
+     * @param string $uid
267
+     * @return string mixed
268
+     */
269
+    private function mapUid($uid) {
270
+        \OC::$server->getURLGenerator()->linkToDocs('key');
271
+        // FIXME this should be a method in the user management instead
272
+        $this->logger->debug('shareWith before, ' . $uid, ['app' => $this->appName]);
273
+        \OCP\Util::emitHook(
274
+            '\OCA\Files_Sharing\API\Server2Server',
275
+            'preLoginNameUsedAsUserName',
276
+            array('uid' => &$uid)
277
+        );
278
+        $this->logger->debug('shareWith after, ' . $uid, ['app' => $this->appName]);
279 279
 
280
-		return $uid;
281
-	}
280
+        return $uid;
281
+    }
282 282
 
283 283
 }
Please login to merge, or discard this patch.
apps/federatedfilesharing/lib/Controller/RequestHandlerController.php 1 patch
Indentation   +550 added lines, -550 removed lines patch added patch discarded remove patch
@@ -56,554 +56,554 @@
 block discarded – undo
56 56
 
57 57
 class RequestHandlerController extends OCSController {
58 58
 
59
-	/** @var FederatedShareProvider */
60
-	private $federatedShareProvider;
61
-
62
-	/** @var IDBConnection */
63
-	private $connection;
64
-
65
-	/** @var Share\IManager */
66
-	private $shareManager;
67
-
68
-	/** @var Notifications */
69
-	private $notifications;
70
-
71
-	/** @var AddressHandler */
72
-	private $addressHandler;
73
-
74
-	/** @var  IUserManager */
75
-	private $userManager;
76
-
77
-	/** @var string */
78
-	private $shareTable = 'share';
79
-
80
-	/** @var ICloudIdManager */
81
-	private $cloudIdManager;
82
-
83
-	/** @var ILogger */
84
-	private $logger;
85
-
86
-	/** @var ICloudFederationFactory */
87
-	private $cloudFederationFactory;
88
-
89
-	/** @var ICloudFederationProviderManager */
90
-	private $cloudFederationProviderManager;
91
-
92
-	/**
93
-	 * Server2Server constructor.
94
-	 *
95
-	 * @param string $appName
96
-	 * @param IRequest $request
97
-	 * @param FederatedShareProvider $federatedShareProvider
98
-	 * @param IDBConnection $connection
99
-	 * @param Share\IManager $shareManager
100
-	 * @param Notifications $notifications
101
-	 * @param AddressHandler $addressHandler
102
-	 * @param IUserManager $userManager
103
-	 * @param ICloudIdManager $cloudIdManager
104
-	 * @param ILogger $logger
105
-	 * @param ICloudFederationFactory $cloudFederationFactory
106
-	 * @param ICloudFederationProviderManager $cloudFederationProviderManager
107
-	 */
108
-	public function __construct($appName,
109
-								IRequest $request,
110
-								FederatedShareProvider $federatedShareProvider,
111
-								IDBConnection $connection,
112
-								Share\IManager $shareManager,
113
-								Notifications $notifications,
114
-								AddressHandler $addressHandler,
115
-								IUserManager $userManager,
116
-								ICloudIdManager $cloudIdManager,
117
-								ILogger $logger,
118
-								ICloudFederationFactory $cloudFederationFactory,
119
-								ICloudFederationProviderManager $cloudFederationProviderManager
120
-	) {
121
-		parent::__construct($appName, $request);
122
-
123
-		$this->federatedShareProvider = $federatedShareProvider;
124
-		$this->connection = $connection;
125
-		$this->shareManager = $shareManager;
126
-		$this->notifications = $notifications;
127
-		$this->addressHandler = $addressHandler;
128
-		$this->userManager = $userManager;
129
-		$this->cloudIdManager = $cloudIdManager;
130
-		$this->logger = $logger;
131
-		$this->cloudFederationFactory = $cloudFederationFactory;
132
-		$this->cloudFederationProviderManager = $cloudFederationProviderManager;
133
-	}
134
-
135
-	/**
136
-	 * @NoCSRFRequired
137
-	 * @PublicPage
138
-	 *
139
-	 * create a new share
140
-	 *
141
-	 * @return Http\DataResponse
142
-	 * @throws OCSException
143
-	 */
144
-	public function createShare() {
145
-
146
-		$remote = isset($_POST['remote']) ? $_POST['remote'] : null;
147
-		$token = isset($_POST['token']) ? $_POST['token'] : null;
148
-		$name = isset($_POST['name']) ? $_POST['name'] : null;
149
-		$owner = isset($_POST['owner']) ? $_POST['owner'] : null;
150
-		$sharedBy = isset($_POST['sharedBy']) ? $_POST['sharedBy'] : null;
151
-		$shareWith = isset($_POST['shareWith']) ? $_POST['shareWith'] : null;
152
-		$remoteId = isset($_POST['remoteId']) ? (int)$_POST['remoteId'] : null;
153
-		$sharedByFederatedId = isset($_POST['sharedByFederatedId']) ? $_POST['sharedByFederatedId'] : null;
154
-		$ownerFederatedId = isset($_POST['ownerFederatedId']) ? $_POST['ownerFederatedId'] : null;
155
-
156
-		if ($ownerFederatedId === null) {
157
-			$ownerFederatedId = $this->cloudIdManager->getCloudId($owner, $this->cleanupRemote($remote))->getId();
158
-		}
159
-		// if the owner of the share and the initiator are the same user
160
-		// we also complete the federated share ID for the initiator
161
-		if ($sharedByFederatedId === null && $owner === $sharedBy) {
162
-			$sharedByFederatedId = $ownerFederatedId;
163
-		}
164
-
165
-		$share = $this->cloudFederationFactory->getCloudFederationShare(
166
-			$shareWith,
167
-			$name,
168
-			'',
169
-			$remoteId,
170
-			$ownerFederatedId,
171
-			$owner,
172
-			$sharedByFederatedId,
173
-			$sharedBy,
174
-			$token,
175
-			'user',
176
-			'file'
177
-		);
178
-
179
-		try {
180
-			$provider = $this->cloudFederationProviderManager->getCloudFederationProvider('file');
181
-			$provider->shareReceived($share);
182
-		} catch (ProviderDoesNotExistsException $e) {
183
-			throw new OCSException('Server does not support federated cloud sharing', 503);
184
-		} catch (ProviderCouldNotAddShareException $e) {
185
-			throw new OCSException($e->getMessage(), $e->getCode());
186
-		} catch (\Exception $e) {
187
-			throw new OCSException('internal server error, was not able to add share from ' . $remote, 500);
188
-		}
189
-
190
-		return new Http\DataResponse();
191
-	}
192
-
193
-	/**
194
-	 * @NoCSRFRequired
195
-	 * @PublicPage
196
-	 *
197
-	 * create re-share on behalf of another user
198
-	 *
199
-	 * @param int $id
200
-	 * @return Http\DataResponse
201
-	 * @throws OCSBadRequestException
202
-	 * @throws OCSForbiddenException
203
-	 * @throws OCSNotFoundException
204
-	 */
205
-	public function reShare($id) {
206
-
207
-		$token = $this->request->getParam('token', null);
208
-		$shareWith = $this->request->getParam('shareWith', null);
209
-		$permission = (int)$this->request->getParam('permission', null);
210
-		$remoteId = (int)$this->request->getParam('remoteId', null);
211
-
212
-		if ($id === null ||
213
-			$token === null ||
214
-			$shareWith === null ||
215
-			$permission === null ||
216
-			$remoteId === null
217
-		) {
218
-			throw new OCSBadRequestException();
219
-		}
220
-
221
-		try {
222
-			$share = $this->federatedShareProvider->getShareById($id);
223
-		} catch (Share\Exceptions\ShareNotFound $e) {
224
-			throw new OCSNotFoundException();
225
-		}
226
-
227
-		// don't allow to share a file back to the owner
228
-		list($user, $remote) = $this->addressHandler->splitUserRemote($shareWith);
229
-		$owner = $share->getShareOwner();
230
-		$currentServer = $this->addressHandler->generateRemoteURL();
231
-		if ($this->addressHandler->compareAddresses($user, $remote, $owner, $currentServer)) {
232
-			throw new OCSForbiddenException();
233
-		}
234
-
235
-		if ($this->verifyShare($share, $token)) {
236
-
237
-			// check if re-sharing is allowed
238
-			if ($share->getPermissions() | ~Constants::PERMISSION_SHARE) {
239
-				$share->setPermissions($share->getPermissions() & $permission);
240
-				// the recipient of the initial share is now the initiator for the re-share
241
-				$share->setSharedBy($share->getSharedWith());
242
-				$share->setSharedWith($shareWith);
243
-				try {
244
-					$result = $this->federatedShareProvider->create($share);
245
-					$this->federatedShareProvider->storeRemoteId((int)$result->getId(), $remoteId);
246
-					return new Http\DataResponse([
247
-						'token' => $result->getToken(),
248
-						'remoteId' => $result->getId()
249
-					]);
250
-				} catch (\Exception $e) {
251
-					throw new OCSBadRequestException();
252
-				}
253
-			} else {
254
-				throw new OCSForbiddenException();
255
-			}
256
-		}
257
-		throw new OCSBadRequestException();
258
-	}
259
-
260
-	/**
261
-	 * @NoCSRFRequired
262
-	 * @PublicPage
263
-	 *
264
-	 * accept server-to-server share
265
-	 *
266
-	 * @param int $id
267
-	 * @return Http\DataResponse
268
-	 * @throws OCSException
269
-	 * @throws Share\Exceptions\ShareNotFound
270
-	 * @throws \OC\HintException
271
-	 */
272
-	public function acceptShare($id) {
273
-
274
-		if (!$this->isS2SEnabled()) {
275
-			throw new OCSException('Server does not support federated cloud sharing', 503);
276
-		}
277
-
278
-		$token = isset($_POST['token']) ? $_POST['token'] : null;
279
-
280
-		$notification = [
281
-			'sharedSecret' => $token,
282
-			'message' => 'Recipient accept the share'
283
-		];
284
-
285
-		try {
286
-			$provider = $this->cloudFederationProviderManager->getCloudFederationProvider('file');
287
-			$provider->notificationReceived('SHARE_ACCEPTED', $id, $notification);
288
-		} catch (ProviderDoesNotExistsException $e) {
289
-			throw new OCSException('Server does not support federated cloud sharing', 503);
290
-		} catch (ShareNotFoundException $e) {
291
-			$this->logger->debug('Share not found: ' . $e->getMessage());
292
-		} catch (\Exception $e) {
293
-			$this->logger->debug('internal server error, can not process notification: ' . $e->getMessage());
294
-		}
295
-
296
-		return new Http\DataResponse();
297
-	}
298
-
299
-	/**
300
-	 * @NoCSRFRequired
301
-	 * @PublicPage
302
-	 *
303
-	 * decline server-to-server share
304
-	 *
305
-	 * @param int $id
306
-	 * @return Http\DataResponse
307
-	 * @throws OCSException
308
-	 */
309
-	public function declineShare($id) {
310
-
311
-		if (!$this->isS2SEnabled()) {
312
-			throw new OCSException('Server does not support federated cloud sharing', 503);
313
-		}
314
-
315
-		$token = isset($_POST['token']) ? $_POST['token'] : null;
316
-
317
-		try {
318
-			$share = $this->federatedShareProvider->getShareById($id);
319
-		} catch (Share\Exceptions\ShareNotFound $e) {
320
-			return new Http\DataResponse();
321
-		}
322
-
323
-		if ($this->verifyShare($share, $token)) {
324
-			if ($share->getShareOwner() !== $share->getSharedBy()) {
325
-				list(, $remote) = $this->addressHandler->splitUserRemote($share->getSharedBy());
326
-				$remoteId = $this->federatedShareProvider->getRemoteId($share);
327
-				$this->notifications->sendDeclineShare($remote, $remoteId, $share->getToken());
328
-			}
329
-			$this->executeDeclineShare($share);
330
-		}
331
-
332
-		return new Http\DataResponse();
333
-	}
334
-
335
-	/**
336
-	 * delete declined share and create a activity
337
-	 *
338
-	 * @param Share\IShare $share
339
-	 */
340
-	protected function executeDeclineShare(Share\IShare $share) {
341
-		$this->federatedShareProvider->removeShareFromTable($share);
342
-		$fileId = (int) $share->getNode()->getId();
343
-		list($file, $link) = $this->getFile($this->getCorrectUid($share), $fileId);
344
-
345
-		$event = \OC::$server->getActivityManager()->generateEvent();
346
-		$event->setApp('files_sharing')
347
-			->setType('remote_share')
348
-			->setAffectedUser($this->getCorrectUid($share))
349
-			->setSubject(RemoteShares::SUBJECT_REMOTE_SHARE_DECLINED, [$share->getSharedWith(), [$fileId => $file]])
350
-			->setObject('files', $fileId, $file)
351
-			->setLink($link);
352
-		\OC::$server->getActivityManager()->publish($event);
353
-
354
-	}
355
-
356
-	/**
357
-	 * @NoCSRFRequired
358
-	 * @PublicPage
359
-	 *
360
-	 * remove server-to-server share if it was unshared by the owner
361
-	 *
362
-	 * @param int $id
363
-	 * @return Http\DataResponse
364
-	 * @throws OCSException
365
-	 */
366
-	public function unshare($id) {
367
-
368
-		if (!$this->isS2SEnabled()) {
369
-			throw new OCSException('Server does not support federated cloud sharing', 503);
370
-		}
371
-
372
-		$token = isset($_POST['token']) ? $_POST['token'] : null;
373
-
374
-		$qb = $this->connection->getQueryBuilder();
375
-		$qb->select('*')
376
-			->from('share_external')
377
-			->where(
378
-				$qb->expr()->andX(
379
-					$qb->expr()->eq('remote_id', $qb->createNamedParameter($id)),
380
-					$qb->expr()->eq('share_token', $qb->createNamedParameter($token))
381
-				)
382
-			);
383
-
384
-		$result = $qb->execute();
385
-		$share = $result->fetch();
386
-		$result->closeCursor();
387
-
388
-		if ($token && $id && !empty($share)) {
389
-
390
-			$remote = $this->cleanupRemote($share['remote']);
391
-
392
-			$owner = $this->cloudIdManager->getCloudId($share['owner'], $remote);
393
-			$mountpoint = $share['mountpoint'];
394
-			$user = $share['user'];
395
-
396
-			$qb = $this->connection->getQueryBuilder();
397
-			$qb->delete('share_external')
398
-				->where(
399
-					$qb->expr()->andX(
400
-						$qb->expr()->eq('remote_id', $qb->createNamedParameter($id)),
401
-						$qb->expr()->eq('share_token', $qb->createNamedParameter($token))
402
-					)
403
-				);
404
-
405
-			$result = $qb->execute();
406
-			$result->closeCursor();
407
-
408
-			if ($share['accepted']) {
409
-				$path = trim($mountpoint, '/');
410
-			} else {
411
-				$path = trim($share['name'], '/');
412
-			}
413
-
414
-			$notificationManager = \OC::$server->getNotificationManager();
415
-			$notification = $notificationManager->createNotification();
416
-			$notification->setApp('files_sharing')
417
-				->setUser($share['user'])
418
-				->setObject('remote_share', (int)$share['id']);
419
-			$notificationManager->markProcessed($notification);
420
-
421
-			$event = \OC::$server->getActivityManager()->generateEvent();
422
-			$event->setApp('files_sharing')
423
-				->setType('remote_share')
424
-				->setSubject(RemoteShares::SUBJECT_REMOTE_SHARE_UNSHARED, [$owner->getId(), $path])
425
-				->setAffectedUser($user)
426
-				->setObject('remote_share', (int)$share['id'], $path);
427
-			\OC::$server->getActivityManager()->publish($event);
428
-		}
429
-
430
-		return new Http\DataResponse();
431
-	}
432
-
433
-	private function cleanupRemote($remote) {
434
-		$remote = substr($remote, strpos($remote, '://') + 3);
435
-
436
-		return rtrim($remote, '/');
437
-	}
438
-
439
-
440
-	/**
441
-	 * @NoCSRFRequired
442
-	 * @PublicPage
443
-	 *
444
-	 * federated share was revoked, either by the owner or the re-sharer
445
-	 *
446
-	 * @param int $id
447
-	 * @return Http\DataResponse
448
-	 * @throws OCSBadRequestException
449
-	 */
450
-	public function revoke($id) {
451
-		$token = $this->request->getParam('token');
452
-
453
-		$share = $this->federatedShareProvider->getShareById($id);
454
-
455
-		if ($this->verifyShare($share, $token)) {
456
-			$this->federatedShareProvider->removeShareFromTable($share);
457
-			return new Http\DataResponse();
458
-		}
459
-
460
-		throw new OCSBadRequestException();
461
-	}
462
-
463
-	/**
464
-	 * get share
465
-	 *
466
-	 * @param int $id
467
-	 * @param string $token
468
-	 * @return array|bool
469
-	 */
470
-	protected function getShare($id, $token) {
471
-		$query = $this->connection->getQueryBuilder();
472
-		$query->select('*')->from($this->shareTable)
473
-			->where($query->expr()->eq('token', $query->createNamedParameter($token)))
474
-			->andWhere($query->expr()->eq('share_type', $query->createNamedParameter(FederatedShareProvider::SHARE_TYPE_REMOTE)))
475
-			->andWhere($query->expr()->eq('id', $query->createNamedParameter($id)));
476
-
477
-		$result = $query->execute()->fetchAll();
478
-
479
-		if (!empty($result) && isset($result[0])) {
480
-			return $result[0];
481
-		}
482
-
483
-		return false;
484
-	}
485
-
486
-	/**
487
-	 * get file
488
-	 *
489
-	 * @param string $user
490
-	 * @param int $fileSource
491
-	 * @return array with internal path of the file and a absolute link to it
492
-	 */
493
-	private function getFile($user, $fileSource) {
494
-		\OC_Util::setupFS($user);
495
-
496
-		try {
497
-			$file = \OC\Files\Filesystem::getPath($fileSource);
498
-		} catch (NotFoundException $e) {
499
-			$file = null;
500
-		}
501
-		$args = \OC\Files\Filesystem::is_dir($file) ? array('dir' => $file) : array('dir' => dirname($file), 'scrollto' => $file);
502
-		$link = \OCP\Util::linkToAbsolute('files', 'index.php', $args);
503
-
504
-		return array($file, $link);
505
-
506
-	}
507
-
508
-	/**
509
-	 * check if server-to-server sharing is enabled
510
-	 *
511
-	 * @param bool $incoming
512
-	 * @return bool
513
-	 */
514
-	private function isS2SEnabled($incoming = false) {
515
-
516
-		$result = \OCP\App::isEnabled('files_sharing');
517
-
518
-		if ($incoming) {
519
-			$result = $result && $this->federatedShareProvider->isIncomingServer2serverShareEnabled();
520
-		} else {
521
-			$result = $result && $this->federatedShareProvider->isOutgoingServer2serverShareEnabled();
522
-		}
523
-
524
-		return $result;
525
-	}
526
-
527
-	/**
528
-	 * @NoCSRFRequired
529
-	 * @PublicPage
530
-	 *
531
-	 * update share information to keep federated re-shares in sync
532
-	 *
533
-	 * @param int $id
534
-	 * @return Http\DataResponse
535
-	 * @throws OCSBadRequestException
536
-	 */
537
-	public function updatePermissions($id) {
538
-		$token = $this->request->getParam('token', null);
539
-		$permissions = $this->request->getParam('permissions', null);
540
-
541
-		try {
542
-			$share = $this->federatedShareProvider->getShareById($id);
543
-		} catch (Share\Exceptions\ShareNotFound $e) {
544
-			throw new OCSBadRequestException();
545
-		}
546
-
547
-		$validPermission = ctype_digit($permissions);
548
-		$validToken = $this->verifyShare($share, $token);
549
-		if ($validPermission && $validToken) {
550
-			$this->updatePermissionsInDatabase($share, (int)$permissions);
551
-		} else {
552
-			throw new OCSBadRequestException();
553
-		}
554
-
555
-		return new Http\DataResponse();
556
-	}
557
-
558
-	/**
559
-	 * update permissions in database
560
-	 *
561
-	 * @param IShare $share
562
-	 * @param int $permissions
563
-	 */
564
-	protected function updatePermissionsInDatabase(IShare $share, $permissions) {
565
-		$query = $this->connection->getQueryBuilder();
566
-		$query->update('share')
567
-			->where($query->expr()->eq('id', $query->createNamedParameter($share->getId())))
568
-			->set('permissions', $query->createNamedParameter($permissions))
569
-			->execute();
570
-	}
571
-
572
-	/**
573
-	 * @NoCSRFRequired
574
-	 * @PublicPage
575
-	 *
576
-	 * change the owner of a server-to-server share
577
-	 *
578
-	 * @param int $id
579
-	 * @return Http\DataResponse
580
-	 * @throws \InvalidArgumentException
581
-	 * @throws OCSException
582
-	 */
583
-	public function move($id) {
584
-
585
-		if (!$this->isS2SEnabled()) {
586
-			throw new OCSException('Server does not support federated cloud sharing', 503);
587
-		}
588
-
589
-		$token = $this->request->getParam('token');
590
-		$remote = $this->request->getParam('remote');
591
-		$newRemoteId = $this->request->getParam('remote_id', $id);
592
-		$cloudId = $this->cloudIdManager->resolveCloudId($remote);
593
-
594
-		$qb = $this->connection->getQueryBuilder();
595
-		$query = $qb->update('share_external')
596
-			->set('remote', $qb->createNamedParameter($cloudId->getRemote()))
597
-			->set('owner', $qb->createNamedParameter($cloudId->getUser()))
598
-			->set('remote_id', $qb->createNamedParameter($newRemoteId))
599
-			->where($qb->expr()->eq('remote_id', $qb->createNamedParameter($id)))
600
-			->andWhere($qb->expr()->eq('share_token', $qb->createNamedParameter($token)));
601
-		$affected = $query->execute();
602
-
603
-		if ($affected > 0) {
604
-			return new Http\DataResponse(['remote' => $cloudId->getRemote(), 'owner' => $cloudId->getUser()]);
605
-		} else {
606
-			throw new OCSBadRequestException('Share not found or token invalid');
607
-		}
608
-	}
59
+    /** @var FederatedShareProvider */
60
+    private $federatedShareProvider;
61
+
62
+    /** @var IDBConnection */
63
+    private $connection;
64
+
65
+    /** @var Share\IManager */
66
+    private $shareManager;
67
+
68
+    /** @var Notifications */
69
+    private $notifications;
70
+
71
+    /** @var AddressHandler */
72
+    private $addressHandler;
73
+
74
+    /** @var  IUserManager */
75
+    private $userManager;
76
+
77
+    /** @var string */
78
+    private $shareTable = 'share';
79
+
80
+    /** @var ICloudIdManager */
81
+    private $cloudIdManager;
82
+
83
+    /** @var ILogger */
84
+    private $logger;
85
+
86
+    /** @var ICloudFederationFactory */
87
+    private $cloudFederationFactory;
88
+
89
+    /** @var ICloudFederationProviderManager */
90
+    private $cloudFederationProviderManager;
91
+
92
+    /**
93
+     * Server2Server constructor.
94
+     *
95
+     * @param string $appName
96
+     * @param IRequest $request
97
+     * @param FederatedShareProvider $federatedShareProvider
98
+     * @param IDBConnection $connection
99
+     * @param Share\IManager $shareManager
100
+     * @param Notifications $notifications
101
+     * @param AddressHandler $addressHandler
102
+     * @param IUserManager $userManager
103
+     * @param ICloudIdManager $cloudIdManager
104
+     * @param ILogger $logger
105
+     * @param ICloudFederationFactory $cloudFederationFactory
106
+     * @param ICloudFederationProviderManager $cloudFederationProviderManager
107
+     */
108
+    public function __construct($appName,
109
+                                IRequest $request,
110
+                                FederatedShareProvider $federatedShareProvider,
111
+                                IDBConnection $connection,
112
+                                Share\IManager $shareManager,
113
+                                Notifications $notifications,
114
+                                AddressHandler $addressHandler,
115
+                                IUserManager $userManager,
116
+                                ICloudIdManager $cloudIdManager,
117
+                                ILogger $logger,
118
+                                ICloudFederationFactory $cloudFederationFactory,
119
+                                ICloudFederationProviderManager $cloudFederationProviderManager
120
+    ) {
121
+        parent::__construct($appName, $request);
122
+
123
+        $this->federatedShareProvider = $federatedShareProvider;
124
+        $this->connection = $connection;
125
+        $this->shareManager = $shareManager;
126
+        $this->notifications = $notifications;
127
+        $this->addressHandler = $addressHandler;
128
+        $this->userManager = $userManager;
129
+        $this->cloudIdManager = $cloudIdManager;
130
+        $this->logger = $logger;
131
+        $this->cloudFederationFactory = $cloudFederationFactory;
132
+        $this->cloudFederationProviderManager = $cloudFederationProviderManager;
133
+    }
134
+
135
+    /**
136
+     * @NoCSRFRequired
137
+     * @PublicPage
138
+     *
139
+     * create a new share
140
+     *
141
+     * @return Http\DataResponse
142
+     * @throws OCSException
143
+     */
144
+    public function createShare() {
145
+
146
+        $remote = isset($_POST['remote']) ? $_POST['remote'] : null;
147
+        $token = isset($_POST['token']) ? $_POST['token'] : null;
148
+        $name = isset($_POST['name']) ? $_POST['name'] : null;
149
+        $owner = isset($_POST['owner']) ? $_POST['owner'] : null;
150
+        $sharedBy = isset($_POST['sharedBy']) ? $_POST['sharedBy'] : null;
151
+        $shareWith = isset($_POST['shareWith']) ? $_POST['shareWith'] : null;
152
+        $remoteId = isset($_POST['remoteId']) ? (int)$_POST['remoteId'] : null;
153
+        $sharedByFederatedId = isset($_POST['sharedByFederatedId']) ? $_POST['sharedByFederatedId'] : null;
154
+        $ownerFederatedId = isset($_POST['ownerFederatedId']) ? $_POST['ownerFederatedId'] : null;
155
+
156
+        if ($ownerFederatedId === null) {
157
+            $ownerFederatedId = $this->cloudIdManager->getCloudId($owner, $this->cleanupRemote($remote))->getId();
158
+        }
159
+        // if the owner of the share and the initiator are the same user
160
+        // we also complete the federated share ID for the initiator
161
+        if ($sharedByFederatedId === null && $owner === $sharedBy) {
162
+            $sharedByFederatedId = $ownerFederatedId;
163
+        }
164
+
165
+        $share = $this->cloudFederationFactory->getCloudFederationShare(
166
+            $shareWith,
167
+            $name,
168
+            '',
169
+            $remoteId,
170
+            $ownerFederatedId,
171
+            $owner,
172
+            $sharedByFederatedId,
173
+            $sharedBy,
174
+            $token,
175
+            'user',
176
+            'file'
177
+        );
178
+
179
+        try {
180
+            $provider = $this->cloudFederationProviderManager->getCloudFederationProvider('file');
181
+            $provider->shareReceived($share);
182
+        } catch (ProviderDoesNotExistsException $e) {
183
+            throw new OCSException('Server does not support federated cloud sharing', 503);
184
+        } catch (ProviderCouldNotAddShareException $e) {
185
+            throw new OCSException($e->getMessage(), $e->getCode());
186
+        } catch (\Exception $e) {
187
+            throw new OCSException('internal server error, was not able to add share from ' . $remote, 500);
188
+        }
189
+
190
+        return new Http\DataResponse();
191
+    }
192
+
193
+    /**
194
+     * @NoCSRFRequired
195
+     * @PublicPage
196
+     *
197
+     * create re-share on behalf of another user
198
+     *
199
+     * @param int $id
200
+     * @return Http\DataResponse
201
+     * @throws OCSBadRequestException
202
+     * @throws OCSForbiddenException
203
+     * @throws OCSNotFoundException
204
+     */
205
+    public function reShare($id) {
206
+
207
+        $token = $this->request->getParam('token', null);
208
+        $shareWith = $this->request->getParam('shareWith', null);
209
+        $permission = (int)$this->request->getParam('permission', null);
210
+        $remoteId = (int)$this->request->getParam('remoteId', null);
211
+
212
+        if ($id === null ||
213
+            $token === null ||
214
+            $shareWith === null ||
215
+            $permission === null ||
216
+            $remoteId === null
217
+        ) {
218
+            throw new OCSBadRequestException();
219
+        }
220
+
221
+        try {
222
+            $share = $this->federatedShareProvider->getShareById($id);
223
+        } catch (Share\Exceptions\ShareNotFound $e) {
224
+            throw new OCSNotFoundException();
225
+        }
226
+
227
+        // don't allow to share a file back to the owner
228
+        list($user, $remote) = $this->addressHandler->splitUserRemote($shareWith);
229
+        $owner = $share->getShareOwner();
230
+        $currentServer = $this->addressHandler->generateRemoteURL();
231
+        if ($this->addressHandler->compareAddresses($user, $remote, $owner, $currentServer)) {
232
+            throw new OCSForbiddenException();
233
+        }
234
+
235
+        if ($this->verifyShare($share, $token)) {
236
+
237
+            // check if re-sharing is allowed
238
+            if ($share->getPermissions() | ~Constants::PERMISSION_SHARE) {
239
+                $share->setPermissions($share->getPermissions() & $permission);
240
+                // the recipient of the initial share is now the initiator for the re-share
241
+                $share->setSharedBy($share->getSharedWith());
242
+                $share->setSharedWith($shareWith);
243
+                try {
244
+                    $result = $this->federatedShareProvider->create($share);
245
+                    $this->federatedShareProvider->storeRemoteId((int)$result->getId(), $remoteId);
246
+                    return new Http\DataResponse([
247
+                        'token' => $result->getToken(),
248
+                        'remoteId' => $result->getId()
249
+                    ]);
250
+                } catch (\Exception $e) {
251
+                    throw new OCSBadRequestException();
252
+                }
253
+            } else {
254
+                throw new OCSForbiddenException();
255
+            }
256
+        }
257
+        throw new OCSBadRequestException();
258
+    }
259
+
260
+    /**
261
+     * @NoCSRFRequired
262
+     * @PublicPage
263
+     *
264
+     * accept server-to-server share
265
+     *
266
+     * @param int $id
267
+     * @return Http\DataResponse
268
+     * @throws OCSException
269
+     * @throws Share\Exceptions\ShareNotFound
270
+     * @throws \OC\HintException
271
+     */
272
+    public function acceptShare($id) {
273
+
274
+        if (!$this->isS2SEnabled()) {
275
+            throw new OCSException('Server does not support federated cloud sharing', 503);
276
+        }
277
+
278
+        $token = isset($_POST['token']) ? $_POST['token'] : null;
279
+
280
+        $notification = [
281
+            'sharedSecret' => $token,
282
+            'message' => 'Recipient accept the share'
283
+        ];
284
+
285
+        try {
286
+            $provider = $this->cloudFederationProviderManager->getCloudFederationProvider('file');
287
+            $provider->notificationReceived('SHARE_ACCEPTED', $id, $notification);
288
+        } catch (ProviderDoesNotExistsException $e) {
289
+            throw new OCSException('Server does not support federated cloud sharing', 503);
290
+        } catch (ShareNotFoundException $e) {
291
+            $this->logger->debug('Share not found: ' . $e->getMessage());
292
+        } catch (\Exception $e) {
293
+            $this->logger->debug('internal server error, can not process notification: ' . $e->getMessage());
294
+        }
295
+
296
+        return new Http\DataResponse();
297
+    }
298
+
299
+    /**
300
+     * @NoCSRFRequired
301
+     * @PublicPage
302
+     *
303
+     * decline server-to-server share
304
+     *
305
+     * @param int $id
306
+     * @return Http\DataResponse
307
+     * @throws OCSException
308
+     */
309
+    public function declineShare($id) {
310
+
311
+        if (!$this->isS2SEnabled()) {
312
+            throw new OCSException('Server does not support federated cloud sharing', 503);
313
+        }
314
+
315
+        $token = isset($_POST['token']) ? $_POST['token'] : null;
316
+
317
+        try {
318
+            $share = $this->federatedShareProvider->getShareById($id);
319
+        } catch (Share\Exceptions\ShareNotFound $e) {
320
+            return new Http\DataResponse();
321
+        }
322
+
323
+        if ($this->verifyShare($share, $token)) {
324
+            if ($share->getShareOwner() !== $share->getSharedBy()) {
325
+                list(, $remote) = $this->addressHandler->splitUserRemote($share->getSharedBy());
326
+                $remoteId = $this->federatedShareProvider->getRemoteId($share);
327
+                $this->notifications->sendDeclineShare($remote, $remoteId, $share->getToken());
328
+            }
329
+            $this->executeDeclineShare($share);
330
+        }
331
+
332
+        return new Http\DataResponse();
333
+    }
334
+
335
+    /**
336
+     * delete declined share and create a activity
337
+     *
338
+     * @param Share\IShare $share
339
+     */
340
+    protected function executeDeclineShare(Share\IShare $share) {
341
+        $this->federatedShareProvider->removeShareFromTable($share);
342
+        $fileId = (int) $share->getNode()->getId();
343
+        list($file, $link) = $this->getFile($this->getCorrectUid($share), $fileId);
344
+
345
+        $event = \OC::$server->getActivityManager()->generateEvent();
346
+        $event->setApp('files_sharing')
347
+            ->setType('remote_share')
348
+            ->setAffectedUser($this->getCorrectUid($share))
349
+            ->setSubject(RemoteShares::SUBJECT_REMOTE_SHARE_DECLINED, [$share->getSharedWith(), [$fileId => $file]])
350
+            ->setObject('files', $fileId, $file)
351
+            ->setLink($link);
352
+        \OC::$server->getActivityManager()->publish($event);
353
+
354
+    }
355
+
356
+    /**
357
+     * @NoCSRFRequired
358
+     * @PublicPage
359
+     *
360
+     * remove server-to-server share if it was unshared by the owner
361
+     *
362
+     * @param int $id
363
+     * @return Http\DataResponse
364
+     * @throws OCSException
365
+     */
366
+    public function unshare($id) {
367
+
368
+        if (!$this->isS2SEnabled()) {
369
+            throw new OCSException('Server does not support federated cloud sharing', 503);
370
+        }
371
+
372
+        $token = isset($_POST['token']) ? $_POST['token'] : null;
373
+
374
+        $qb = $this->connection->getQueryBuilder();
375
+        $qb->select('*')
376
+            ->from('share_external')
377
+            ->where(
378
+                $qb->expr()->andX(
379
+                    $qb->expr()->eq('remote_id', $qb->createNamedParameter($id)),
380
+                    $qb->expr()->eq('share_token', $qb->createNamedParameter($token))
381
+                )
382
+            );
383
+
384
+        $result = $qb->execute();
385
+        $share = $result->fetch();
386
+        $result->closeCursor();
387
+
388
+        if ($token && $id && !empty($share)) {
389
+
390
+            $remote = $this->cleanupRemote($share['remote']);
391
+
392
+            $owner = $this->cloudIdManager->getCloudId($share['owner'], $remote);
393
+            $mountpoint = $share['mountpoint'];
394
+            $user = $share['user'];
395
+
396
+            $qb = $this->connection->getQueryBuilder();
397
+            $qb->delete('share_external')
398
+                ->where(
399
+                    $qb->expr()->andX(
400
+                        $qb->expr()->eq('remote_id', $qb->createNamedParameter($id)),
401
+                        $qb->expr()->eq('share_token', $qb->createNamedParameter($token))
402
+                    )
403
+                );
404
+
405
+            $result = $qb->execute();
406
+            $result->closeCursor();
407
+
408
+            if ($share['accepted']) {
409
+                $path = trim($mountpoint, '/');
410
+            } else {
411
+                $path = trim($share['name'], '/');
412
+            }
413
+
414
+            $notificationManager = \OC::$server->getNotificationManager();
415
+            $notification = $notificationManager->createNotification();
416
+            $notification->setApp('files_sharing')
417
+                ->setUser($share['user'])
418
+                ->setObject('remote_share', (int)$share['id']);
419
+            $notificationManager->markProcessed($notification);
420
+
421
+            $event = \OC::$server->getActivityManager()->generateEvent();
422
+            $event->setApp('files_sharing')
423
+                ->setType('remote_share')
424
+                ->setSubject(RemoteShares::SUBJECT_REMOTE_SHARE_UNSHARED, [$owner->getId(), $path])
425
+                ->setAffectedUser($user)
426
+                ->setObject('remote_share', (int)$share['id'], $path);
427
+            \OC::$server->getActivityManager()->publish($event);
428
+        }
429
+
430
+        return new Http\DataResponse();
431
+    }
432
+
433
+    private function cleanupRemote($remote) {
434
+        $remote = substr($remote, strpos($remote, '://') + 3);
435
+
436
+        return rtrim($remote, '/');
437
+    }
438
+
439
+
440
+    /**
441
+     * @NoCSRFRequired
442
+     * @PublicPage
443
+     *
444
+     * federated share was revoked, either by the owner or the re-sharer
445
+     *
446
+     * @param int $id
447
+     * @return Http\DataResponse
448
+     * @throws OCSBadRequestException
449
+     */
450
+    public function revoke($id) {
451
+        $token = $this->request->getParam('token');
452
+
453
+        $share = $this->federatedShareProvider->getShareById($id);
454
+
455
+        if ($this->verifyShare($share, $token)) {
456
+            $this->federatedShareProvider->removeShareFromTable($share);
457
+            return new Http\DataResponse();
458
+        }
459
+
460
+        throw new OCSBadRequestException();
461
+    }
462
+
463
+    /**
464
+     * get share
465
+     *
466
+     * @param int $id
467
+     * @param string $token
468
+     * @return array|bool
469
+     */
470
+    protected function getShare($id, $token) {
471
+        $query = $this->connection->getQueryBuilder();
472
+        $query->select('*')->from($this->shareTable)
473
+            ->where($query->expr()->eq('token', $query->createNamedParameter($token)))
474
+            ->andWhere($query->expr()->eq('share_type', $query->createNamedParameter(FederatedShareProvider::SHARE_TYPE_REMOTE)))
475
+            ->andWhere($query->expr()->eq('id', $query->createNamedParameter($id)));
476
+
477
+        $result = $query->execute()->fetchAll();
478
+
479
+        if (!empty($result) && isset($result[0])) {
480
+            return $result[0];
481
+        }
482
+
483
+        return false;
484
+    }
485
+
486
+    /**
487
+     * get file
488
+     *
489
+     * @param string $user
490
+     * @param int $fileSource
491
+     * @return array with internal path of the file and a absolute link to it
492
+     */
493
+    private function getFile($user, $fileSource) {
494
+        \OC_Util::setupFS($user);
495
+
496
+        try {
497
+            $file = \OC\Files\Filesystem::getPath($fileSource);
498
+        } catch (NotFoundException $e) {
499
+            $file = null;
500
+        }
501
+        $args = \OC\Files\Filesystem::is_dir($file) ? array('dir' => $file) : array('dir' => dirname($file), 'scrollto' => $file);
502
+        $link = \OCP\Util::linkToAbsolute('files', 'index.php', $args);
503
+
504
+        return array($file, $link);
505
+
506
+    }
507
+
508
+    /**
509
+     * check if server-to-server sharing is enabled
510
+     *
511
+     * @param bool $incoming
512
+     * @return bool
513
+     */
514
+    private function isS2SEnabled($incoming = false) {
515
+
516
+        $result = \OCP\App::isEnabled('files_sharing');
517
+
518
+        if ($incoming) {
519
+            $result = $result && $this->federatedShareProvider->isIncomingServer2serverShareEnabled();
520
+        } else {
521
+            $result = $result && $this->federatedShareProvider->isOutgoingServer2serverShareEnabled();
522
+        }
523
+
524
+        return $result;
525
+    }
526
+
527
+    /**
528
+     * @NoCSRFRequired
529
+     * @PublicPage
530
+     *
531
+     * update share information to keep federated re-shares in sync
532
+     *
533
+     * @param int $id
534
+     * @return Http\DataResponse
535
+     * @throws OCSBadRequestException
536
+     */
537
+    public function updatePermissions($id) {
538
+        $token = $this->request->getParam('token', null);
539
+        $permissions = $this->request->getParam('permissions', null);
540
+
541
+        try {
542
+            $share = $this->federatedShareProvider->getShareById($id);
543
+        } catch (Share\Exceptions\ShareNotFound $e) {
544
+            throw new OCSBadRequestException();
545
+        }
546
+
547
+        $validPermission = ctype_digit($permissions);
548
+        $validToken = $this->verifyShare($share, $token);
549
+        if ($validPermission && $validToken) {
550
+            $this->updatePermissionsInDatabase($share, (int)$permissions);
551
+        } else {
552
+            throw new OCSBadRequestException();
553
+        }
554
+
555
+        return new Http\DataResponse();
556
+    }
557
+
558
+    /**
559
+     * update permissions in database
560
+     *
561
+     * @param IShare $share
562
+     * @param int $permissions
563
+     */
564
+    protected function updatePermissionsInDatabase(IShare $share, $permissions) {
565
+        $query = $this->connection->getQueryBuilder();
566
+        $query->update('share')
567
+            ->where($query->expr()->eq('id', $query->createNamedParameter($share->getId())))
568
+            ->set('permissions', $query->createNamedParameter($permissions))
569
+            ->execute();
570
+    }
571
+
572
+    /**
573
+     * @NoCSRFRequired
574
+     * @PublicPage
575
+     *
576
+     * change the owner of a server-to-server share
577
+     *
578
+     * @param int $id
579
+     * @return Http\DataResponse
580
+     * @throws \InvalidArgumentException
581
+     * @throws OCSException
582
+     */
583
+    public function move($id) {
584
+
585
+        if (!$this->isS2SEnabled()) {
586
+            throw new OCSException('Server does not support federated cloud sharing', 503);
587
+        }
588
+
589
+        $token = $this->request->getParam('token');
590
+        $remote = $this->request->getParam('remote');
591
+        $newRemoteId = $this->request->getParam('remote_id', $id);
592
+        $cloudId = $this->cloudIdManager->resolveCloudId($remote);
593
+
594
+        $qb = $this->connection->getQueryBuilder();
595
+        $query = $qb->update('share_external')
596
+            ->set('remote', $qb->createNamedParameter($cloudId->getRemote()))
597
+            ->set('owner', $qb->createNamedParameter($cloudId->getUser()))
598
+            ->set('remote_id', $qb->createNamedParameter($newRemoteId))
599
+            ->where($qb->expr()->eq('remote_id', $qb->createNamedParameter($id)))
600
+            ->andWhere($qb->expr()->eq('share_token', $qb->createNamedParameter($token)));
601
+        $affected = $query->execute();
602
+
603
+        if ($affected > 0) {
604
+            return new Http\DataResponse(['remote' => $cloudId->getRemote(), 'owner' => $cloudId->getUser()]);
605
+        } else {
606
+            throw new OCSBadRequestException('Share not found or token invalid');
607
+        }
608
+    }
609 609
 }
Please login to merge, or discard this patch.