1
|
|
|
<?php |
2
|
|
|
|
3
|
|
|
declare(strict_types=1); |
4
|
|
|
|
5
|
|
|
|
6
|
|
|
/** |
7
|
|
|
* Circles - Bring cloud-users closer together. |
8
|
|
|
* |
9
|
|
|
* This file is licensed under the Affero General Public License version 3 or |
10
|
|
|
* later. See the COPYING file. |
11
|
|
|
* |
12
|
|
|
* @author Maxence Lange <[email protected]> |
13
|
|
|
* @copyright 2021 |
14
|
|
|
* @license GNU AGPL version 3 or any later version |
15
|
|
|
* |
16
|
|
|
* This program is free software: you can redistribute it and/or modify |
17
|
|
|
* it under the terms of the GNU Affero General Public License as |
18
|
|
|
* published by the Free Software Foundation, either version 3 of the |
19
|
|
|
* License, or (at your option) any later version. |
20
|
|
|
* |
21
|
|
|
* This program is distributed in the hope that it will be useful, |
22
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
23
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
24
|
|
|
* GNU Affero General Public License for more details. |
25
|
|
|
* |
26
|
|
|
* You should have received a copy of the GNU Affero General Public License |
27
|
|
|
* along with this program. If not, see <http://www.gnu.org/licenses/>. |
28
|
|
|
* |
29
|
|
|
*/ |
30
|
|
|
|
31
|
|
|
|
32
|
|
|
namespace OCA\Circles\Service; |
33
|
|
|
|
34
|
|
|
|
35
|
|
|
use daita\MySmallPhpTools\Model\SimpleDataStore; |
36
|
|
|
use daita\MySmallPhpTools\Traits\Nextcloud\nc22\TNC22Logger; |
37
|
|
|
use daita\MySmallPhpTools\Traits\TArrayTools; |
38
|
|
|
use daita\MySmallPhpTools\Traits\TStringTools; |
39
|
|
|
use OCA\Circles\Db\CircleRequest; |
40
|
|
|
use OCA\Circles\Db\MemberRequest; |
41
|
|
|
use OCA\Circles\Exceptions\CircleNotFoundException; |
42
|
|
|
use OCA\Circles\Exceptions\ContactAddressBookNotFoundException; |
43
|
|
|
use OCA\Circles\Exceptions\ContactFormatException; |
44
|
|
|
use OCA\Circles\Exceptions\ContactNotFoundException; |
45
|
|
|
use OCA\Circles\Exceptions\FederatedEventException; |
46
|
|
|
use OCA\Circles\Exceptions\FederatedItemException; |
47
|
|
|
use OCA\Circles\Exceptions\FederatedUserException; |
48
|
|
|
use OCA\Circles\Exceptions\InitiatorNotConfirmedException; |
49
|
|
|
use OCA\Circles\Exceptions\InitiatorNotFoundException; |
50
|
|
|
use OCA\Circles\Exceptions\InvalidIdException; |
51
|
|
|
use OCA\Circles\Exceptions\MemberNotFoundException; |
52
|
|
|
use OCA\Circles\Exceptions\OwnerNotFoundException; |
53
|
|
|
use OCA\Circles\Exceptions\RemoteInstanceException; |
54
|
|
|
use OCA\Circles\Exceptions\RemoteNotFoundException; |
55
|
|
|
use OCA\Circles\Exceptions\RemoteResourceNotFoundException; |
56
|
|
|
use OCA\Circles\Exceptions\RequestBuilderException; |
57
|
|
|
use OCA\Circles\Exceptions\SingleCircleNotFoundException; |
58
|
|
|
use OCA\Circles\Exceptions\UnknownRemoteException; |
59
|
|
|
use OCA\Circles\FederatedItems\MassiveMemberAdd; |
60
|
|
|
use OCA\Circles\FederatedItems\MemberLevel; |
61
|
|
|
use OCA\Circles\FederatedItems\MemberRemove; |
62
|
|
|
use OCA\Circles\FederatedItems\SingleMemberAdd; |
63
|
|
|
use OCA\Circles\IFederatedUser; |
64
|
|
|
use OCA\Circles\Model\Federated\FederatedEvent; |
65
|
|
|
use OCA\Circles\Model\FederatedUser; |
66
|
|
|
use OCA\Circles\Model\Member; |
67
|
|
|
|
68
|
|
|
|
69
|
|
|
/** |
70
|
|
|
* Class MemberService |
71
|
|
|
* |
72
|
|
|
* @package OCA\Circles\Service |
73
|
|
|
*/ |
74
|
|
|
class MemberService { |
75
|
|
|
|
76
|
|
|
|
77
|
|
|
use TArrayTools; |
78
|
|
|
use TStringTools; |
79
|
|
|
use TNC22Logger; |
80
|
|
|
|
81
|
|
|
|
82
|
|
|
/** @var CircleRequest */ |
83
|
|
|
private $circleRequest; |
84
|
|
|
|
85
|
|
|
/** @var MemberRequest */ |
86
|
|
|
private $memberRequest; |
87
|
|
|
|
88
|
|
|
/** @var FederatedUserService */ |
89
|
|
|
private $federatedUserService; |
90
|
|
|
|
91
|
|
|
/** @var MembershipService */ |
92
|
|
|
private $membershipService; |
93
|
|
|
|
94
|
|
|
/** @var FederatedEventService */ |
95
|
|
|
private $federatedEventService; |
96
|
|
|
|
97
|
|
|
/** @var RemoteStreamService */ |
98
|
|
|
private $remoteStreamService; |
99
|
|
|
|
100
|
|
|
|
101
|
|
|
/** |
102
|
|
|
* MemberService constructor. |
103
|
|
|
* |
104
|
|
|
* @param CircleRequest $circleRequest |
105
|
|
|
* @param MemberRequest $memberRequest |
106
|
|
|
* @param FederatedUserService $federatedUserService |
107
|
|
|
* @param FederatedEventService $federatedEventService |
108
|
|
|
* @param RemoteStreamService $remoteStreamService |
109
|
|
|
*/ |
110
|
|
View Code Duplication |
public function __construct( |
|
|
|
|
111
|
|
|
CircleRequest $circleRequest, |
112
|
|
|
MemberRequest $memberRequest, |
113
|
|
|
FederatedUserService $federatedUserService, |
114
|
|
|
MembershipService $membershipService, |
115
|
|
|
FederatedEventService $federatedEventService, |
116
|
|
|
RemoteStreamService $remoteStreamService |
117
|
|
|
) { |
118
|
|
|
$this->circleRequest = $circleRequest; |
119
|
|
|
$this->memberRequest = $memberRequest; |
120
|
|
|
$this->federatedUserService = $federatedUserService; |
121
|
|
|
$this->membershipService = $membershipService; |
122
|
|
|
$this->federatedEventService = $federatedEventService; |
123
|
|
|
$this->remoteStreamService = $remoteStreamService; |
124
|
|
|
} |
125
|
|
|
|
126
|
|
|
// |
127
|
|
|
// /** |
128
|
|
|
// * @param Member $member |
129
|
|
|
// * |
130
|
|
|
// * @throws MemberAlreadyExistsException |
131
|
|
|
// */ |
132
|
|
|
// public function saveMember(Member $member) { |
133
|
|
|
// $member->setId($this->token(Member::ID_LENGTH)); |
134
|
|
|
// $this->memberRequest->save($member); |
135
|
|
|
// } |
136
|
|
|
// |
137
|
|
|
|
138
|
|
|
|
139
|
|
|
/** |
140
|
|
|
* @param string $memberId |
141
|
|
|
* @param string $circleId |
142
|
|
|
* @param bool $canBeVisitor |
143
|
|
|
* |
144
|
|
|
* @return Member |
145
|
|
|
* @throws InitiatorNotFoundException |
146
|
|
|
* @throws MemberNotFoundException |
147
|
|
|
* @throws RequestBuilderException |
148
|
|
|
*/ |
149
|
|
|
public function getMemberById( |
150
|
|
|
string $memberId, |
151
|
|
|
string $circleId = '', |
152
|
|
|
bool $canBeVisitor = false |
153
|
|
|
): Member { |
154
|
|
|
$this->federatedUserService->mustHaveCurrentUser(); |
155
|
|
|
|
156
|
|
|
$member = |
157
|
|
|
$this->memberRequest->getMemberById( |
158
|
|
|
$memberId, |
159
|
|
|
$this->federatedUserService->getCurrentUser(), |
160
|
|
|
$canBeVisitor |
161
|
|
|
); |
162
|
|
|
if ($circleId !== '' && $member->getCircle()->getSingleId() !== $circleId) { |
163
|
|
|
throw new MemberNotFoundException(); |
164
|
|
|
} |
165
|
|
|
|
166
|
|
|
return $member; |
167
|
|
|
} |
168
|
|
|
|
169
|
|
|
|
170
|
|
|
/** |
171
|
|
|
* @param string $circleId |
172
|
|
|
* |
173
|
|
|
* @return Member[] |
174
|
|
|
* @throws InitiatorNotFoundException |
175
|
|
|
* @throws RequestBuilderException |
176
|
|
|
*/ |
177
|
|
|
public function getMembers(string $circleId): array { |
178
|
|
|
$this->federatedUserService->mustHaveCurrentUser(); |
179
|
|
|
|
180
|
|
|
return $this->memberRequest->getMembers( |
181
|
|
|
$circleId, |
182
|
|
|
$this->federatedUserService->getCurrentUser(), |
183
|
|
|
$this->federatedUserService->getRemoteInstance() |
184
|
|
|
); |
185
|
|
|
} |
186
|
|
|
|
187
|
|
|
|
188
|
|
|
/** |
189
|
|
|
* @param string $circleId |
190
|
|
|
* @param FederatedUser $federatedUser |
191
|
|
|
* |
192
|
|
|
* @return array |
193
|
|
|
* @throws CircleNotFoundException |
194
|
|
|
* @throws FederatedEventException |
195
|
|
|
* @throws FederatedItemException |
196
|
|
|
* @throws InitiatorNotConfirmedException |
197
|
|
|
* @throws InitiatorNotFoundException |
198
|
|
|
* @throws OwnerNotFoundException |
199
|
|
|
* @throws RemoteInstanceException |
200
|
|
|
* @throws RemoteNotFoundException |
201
|
|
|
* @throws RemoteResourceNotFoundException |
202
|
|
|
* @throws RequestBuilderException |
203
|
|
|
* @throws UnknownRemoteException |
204
|
|
|
* @throws ContactAddressBookNotFoundException |
205
|
|
|
* @throws ContactFormatException |
206
|
|
|
* @throws ContactNotFoundException |
207
|
|
|
* @throws FederatedUserException |
208
|
|
|
* @throws InvalidIdException |
209
|
|
|
* @throws SingleCircleNotFoundException |
210
|
|
|
*/ |
211
|
|
|
public function addMember(string $circleId, FederatedUser $federatedUser): array { |
212
|
|
|
$this->federatedUserService->mustHaveCurrentUser(); |
213
|
|
|
$circle = $this->circleRequest->getCircle($circleId, $this->federatedUserService->getCurrentUser()); |
214
|
|
|
|
215
|
|
|
$member = new Member(); |
216
|
|
|
$member->importFromIFederatedUser($federatedUser); |
217
|
|
|
|
218
|
|
|
$this->federatedUserService->setMemberPatron($member); |
219
|
|
|
|
220
|
|
|
$event = new FederatedEvent(SingleMemberAdd::class); |
221
|
|
|
$event->setCircle($circle); |
222
|
|
|
$event->setMember($member); |
223
|
|
|
|
224
|
|
|
$this->federatedEventService->newEvent($event); |
225
|
|
|
|
226
|
|
|
return $event->getOutcome(); |
227
|
|
|
} |
228
|
|
|
|
229
|
|
|
|
230
|
|
|
/** |
231
|
|
|
* @param string $circleId |
232
|
|
|
* @param IFederatedUser[] $members |
|
|
|
|
233
|
|
|
* |
234
|
|
|
* @return FederatedUser[] |
235
|
|
|
* @throws CircleNotFoundException |
236
|
|
|
* @throws FederatedEventException |
237
|
|
|
* @throws FederatedItemException |
238
|
|
|
* @throws InitiatorNotConfirmedException |
239
|
|
|
* @throws InitiatorNotFoundException |
240
|
|
|
* @throws OwnerNotFoundException |
241
|
|
|
* @throws RemoteNotFoundException |
242
|
|
|
* @throws RemoteResourceNotFoundException |
243
|
|
|
* @throws UnknownRemoteException |
244
|
|
|
* @throws RemoteInstanceException |
245
|
|
|
* @throws RequestBuilderException |
246
|
|
|
*/ |
247
|
|
|
public function addMembers(string $circleId, array $federatedUsers): array { |
248
|
|
|
$this->federatedUserService->mustHaveCurrentUser(); |
249
|
|
|
$circle = $this->circleRequest->getCircle($circleId, $this->federatedUserService->getCurrentUser()); |
250
|
|
|
|
251
|
|
|
if ($this->federatedUserService->isInitiatedByOcc()) { |
252
|
|
|
$patron = $this->federatedUserService->getAppInitiator('occ', Member::APP_OCC); |
253
|
|
|
} else { |
254
|
|
|
$patron = $this->federatedUserService->getCurrentUser(); |
255
|
|
|
} |
256
|
|
|
|
257
|
|
|
$members = array_map( |
258
|
|
|
function(FederatedUser $federatedUser) use ($patron) { |
259
|
|
|
$member = new Member(); |
260
|
|
|
$member->importFromIFederatedUser($federatedUser); |
261
|
|
|
$member->setInvitedBy($patron); |
|
|
|
|
262
|
|
|
|
263
|
|
|
return $member; |
264
|
|
|
}, $federatedUsers |
265
|
|
|
); |
266
|
|
|
|
267
|
|
|
$event = new FederatedEvent(MassiveMemberAdd::class); |
268
|
|
|
$event->setCircle($circle); |
269
|
|
|
$event->setMembers($members); |
270
|
|
|
$event->setParams(new SimpleDataStore(['federatedUsers' => $members])); |
271
|
|
|
|
272
|
|
|
$this->federatedEventService->newEvent($event); |
273
|
|
|
|
274
|
|
|
return $event->getOutcome(); |
275
|
|
|
} |
276
|
|
|
|
277
|
|
|
|
278
|
|
|
/** |
279
|
|
|
* @param string $memberId |
280
|
|
|
* |
281
|
|
|
* @return array |
282
|
|
|
* @throws FederatedEventException |
283
|
|
|
* @throws FederatedItemException |
284
|
|
|
* @throws InitiatorNotConfirmedException |
285
|
|
|
* @throws InitiatorNotFoundException |
286
|
|
|
* @throws MemberNotFoundException |
287
|
|
|
* @throws OwnerNotFoundException |
288
|
|
|
* @throws RemoteNotFoundException |
289
|
|
|
* @throws RemoteResourceNotFoundException |
290
|
|
|
* @throws UnknownRemoteException |
291
|
|
|
* @throws RequestBuilderException |
292
|
|
|
*/ |
293
|
|
|
public function removeMember(string $memberId): array { |
294
|
|
|
$this->federatedUserService->mustHaveCurrentUser(); |
295
|
|
|
$member = |
296
|
|
|
$this->memberRequest->getMemberById($memberId, $this->federatedUserService->getCurrentUser()); |
297
|
|
|
|
298
|
|
|
$event = new FederatedEvent(MemberRemove::class); |
299
|
|
|
$event->setCircle($member->getCircle()); |
300
|
|
|
$event->setMember($member); |
301
|
|
|
|
302
|
|
|
$this->federatedEventService->newEvent($event); |
303
|
|
|
|
304
|
|
|
return $event->getOutcome(); |
305
|
|
|
} |
306
|
|
|
|
307
|
|
|
/** |
308
|
|
|
* @param string $memberId |
309
|
|
|
* @param int $level |
310
|
|
|
* |
311
|
|
|
* @return array |
312
|
|
|
* @throws FederatedEventException |
313
|
|
|
* @throws InitiatorNotConfirmedException |
314
|
|
|
* @throws InitiatorNotFoundException |
315
|
|
|
* @throws MemberNotFoundException |
316
|
|
|
* @throws OwnerNotFoundException |
317
|
|
|
* @throws RemoteNotFoundException |
318
|
|
|
* @throws RemoteResourceNotFoundException |
319
|
|
|
* @throws UnknownRemoteException |
320
|
|
|
* @throws FederatedItemException |
321
|
|
|
* @throws RequestBuilderException |
322
|
|
|
*/ |
323
|
|
|
public function memberLevel(string $memberId, int $level): array { |
324
|
|
|
$this->federatedUserService->mustHaveCurrentUser(); |
325
|
|
|
$member = |
326
|
|
|
$this->memberRequest->getMemberById($memberId, $this->federatedUserService->getCurrentUser()); |
327
|
|
|
|
328
|
|
|
$event = new FederatedEvent(MemberLevel::class); |
329
|
|
|
$event->setCircle($member->getCircle()); |
330
|
|
|
$event->setMember($member); |
331
|
|
|
$event->setParams(new SimpleDataStore(['level' => $level])); |
332
|
|
|
|
333
|
|
|
$this->federatedEventService->newEvent($event); |
334
|
|
|
|
335
|
|
|
return $event->getOutcome(); |
336
|
|
|
} |
337
|
|
|
|
338
|
|
|
|
339
|
|
|
/** |
340
|
|
|
* @param Member $member |
341
|
|
|
* |
342
|
|
|
* @return bool |
343
|
|
|
* @throws InvalidIdException |
344
|
|
|
* @throws RemoteNotFoundException |
345
|
|
|
* @throws RequestBuilderException |
346
|
|
|
* @throws UnknownRemoteException |
347
|
|
|
*/ |
348
|
|
|
public function insertOrUpdate(Member $member): bool { |
349
|
|
|
try { |
350
|
|
|
$this->federatedUserService->confirmSingleIdUniqueness($member); |
351
|
|
|
|
352
|
|
|
$member->setNoteObj('invitedBy', $member->getInvitedBy()); |
353
|
|
|
|
354
|
|
|
$this->memberRequest->insertOrUpdate($member); |
355
|
|
|
$this->membershipService->onUpdate($member->getSingleId()); |
356
|
|
|
} catch (FederatedUserException $e) { |
357
|
|
|
$this->e($e, ['member' => $member]); |
358
|
|
|
|
359
|
|
|
return false; |
360
|
|
|
} |
361
|
|
|
|
362
|
|
|
return true; |
363
|
|
|
} |
364
|
|
|
|
365
|
|
|
} |
366
|
|
|
|
367
|
|
|
|
Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.
You can also find more detailed suggestions in the “Code” section of your repository.