Bitrix-D7 23.9
 
Загрузка...
Поиск...
Не найдено
voteaccesscontroller.php
1<?php
2
4
11use Bitrix\Tasks\Access\ActionDictionary;
12use Bitrix\Tasks\Access\TaskAccessController;
14
16{
17 private const STEP_LIMIT = 200;
18
19 private $userId;
20 private static $accessCodes = [];
21 private static $userGroups = [];
22
27 public static function beforeGetVoteList(array $info): array
28 {
29 return self::checkEvent($info);
30 }
31
37 public static function afterGetVoteList(array $param, array $items): array
38 {
39 if (
40 !array_key_exists('CHECK_RIGHTS', $param)
41 || $param['CHECK_RIGHTS'] !== 'Y'
42 )
43 {
44 return [
45 'ITEMS' => $items,
46 ];
47 }
48
49 if (array_key_exists('CURRENT_USER_ID', $param))
50 {
51 $userId = (int) $param['CURRENT_USER_ID'];
52 }
53 else
54 {
55 global $USER;
56 $userId = (int) $USER->getId();
57 }
58
59 $userIds = array_column($items, 'ID');
60
61 $controller = new self($userId);
62 $filtered = $controller->filterUsers($userIds);
63
64 if (empty($filtered))
65 {
66 return [
67 'ITEMS' => [],
68 ];
69 }
70
71 foreach ($items as $k => $item)
72 {
73 if (!in_array($item['ID'], $filtered))
74 {
75 unset($items[$k]);
76 }
77 }
78
79 return [
80 'ITEMS' => $items,
81 ];
82 }
83
88 public static function checkEvent(array $info = []): array
89 {
90 $result = new VoteAccessResult();
91 $result
92 ->setResult(true)
93 ->setMessage('')
94 ->setErrorType('');
95
96 if (
97 !array_key_exists('CHECK_RIGHTS', $info)
98 || $info['CHECK_RIGHTS'] !== 'Y'
99 )
100 {
101 return $result->toArray();
102 }
103
104 if (array_key_exists('CURRENT_USER_ID', $info))
105 {
106 $userId = (int) $info['CURRENT_USER_ID'];
107 }
108 else
109 {
110 global $USER;
111 $userId = (int) $USER->getId();
112 }
113
114 if (!array_key_exists('ENTITY_TYPE_ID', $info))
115 {
116 return $result->toArray();
117 }
118 $entityTypeId = (string) $info['ENTITY_TYPE_ID'];
119
120 if (!array_key_exists('ENTITY_ID', $info))
121 {
122 return $result->toArray();
123 }
124 $entityId = (int) $info['ENTITY_ID'];
125
126 $controller = new self($userId);
127 if (!$controller->check($entityTypeId, $entityId))
128 {
129 return (new VoteAccessResult())->toArray();
130 }
131
132 return $result->toArray();
133 }
134
135 public function __construct(int $userId = 0)
136 {
137 $this->userId = $userId;
138 }
139
148 public function check(string $typeId, int $entityId): bool
149 {
150 if (!$this->userId)
151 {
152 return false;
153 }
154
155 // $types = Provider::getEntityTypes();
156
157 $logId = $this->getLogId($typeId, $entityId);
158 // if (
159 // !in_array($typeId, $types)
160 // && !$logId
161 // )
162 // {
163 // // do nothing if there is no record
164 // return true;
165 // }
166
167 if (!$logId)
168 {
169 return true;
170 }
171
172 $logRights = $this->getLogRights($logId);
173 if (empty($logRights))
174 {
175 // this mean that socnet haven't got control for access right for log entry
176 return true;
177 }
178
179 if ($this->isExtranetUser($this->userId))
180 {
181 $extranetSiteId = \CExtranet::GetExtranetSiteID();
182 $logSites = $this->getLogSites($logId);
183
184 if (!in_array($extranetSiteId, $logSites))
185 {
186 return false;
187 }
188 }
189
190 if (in_array("UA", $logRights))
191 {
192 return true;
193 }
194
195 if (
196 in_array("AU", $logRights)
197 && $this->userId
198 )
199 {
200 return true;
201 }
202
203 $accessCodes = $this->getAccessCodes();
204 $isAccess = !empty(array_intersect($accessCodes, $logRights));
205
206 if (
207 $typeId === 'TASK'
208 && Loader::includeModule('tasks')
209 )
210 {
211 $isAccess = $isAccess || TaskAccessController::can($this->userId, ActionDictionary::ACTION_TASK_READ, $entityId);
212 }
213
214 return $isAccess;
215 }
216
224 public function filterUsers(array $userIds): array
225 {
226 if (!$this->isExtranetUser($this->userId))
227 {
228 return $userIds;
229 }
230
231 $userIds = array_map(function($el) {
232 return (int) $el;
233 }, $userIds);
234
235 $userGroups = $this->getUserGroups();
236 if (empty($userGroups))
237 {
238 return [];
239 }
240
241 $chunks = array_chunk($userIds, self::STEP_LIMIT);
242
243 $result = [];
244 foreach ($chunks as $chunk)
245 {
246 $groupUsers = UserToGroupTable::getList([
247 'select' => ['USER_ID'],
248 'filter' => [
249 '@USER_ID' => $chunk,
250 '@GROUP_ID' => $userGroups,
252 ],
253 ])->fetchAll();
254 $groupUsers = array_column($groupUsers, 'USER_ID');
255 $groupUsers = array_intersect($userIds, $groupUsers);
256
257 $result = array_merge($result, $groupUsers);
258 }
259
260 return array_unique($result);
261 }
262
269 private function getUserGroups(): array
270 {
271 if (array_key_exists($this->userId, self::$userGroups))
272 {
273 return self::$userGroups[$this->userId];
274 }
275
276 self::$userGroups[$this->userId] = [];
277
278 $groups = UserToGroupTable::getList([
279 'select' => ['GROUP_ID'],
280 'filter' => [
281 '=USER_ID' => $this->userId,
283 ],
284 ])->fetchAll();
285
286 self::$userGroups[$this->userId] = array_column($groups, 'GROUP_ID');
287
288 return self::$userGroups[$this->userId];
289 }
290
298 private function getLogRights(int $logId): array
299 {
300 $rights = LogRightTable::getList([
301 'select' => ['GROUP_CODE'],
302 'filter' => [
303 '=LOG_ID' => $logId,
304 ],
305 ])->fetchAll();
306
307 $rights = array_column($rights, 'GROUP_CODE');
308 $rights[] = "SA";
309
310 return $rights;
311 }
312
320 private function getLogSites(int $logId): array
321 {
322 $sites = LogSiteTable::getList([
323 'select' => ['SITE_ID'],
324 'filter' => [
325 '=LOG_ID' => $logId,
326 ],
327 ])->fetchAll();
328
329 $sites = array_column($sites, 'SITE_ID');
330
331 return $sites;
332 }
333
337 private function getAccessCodes()
338 {
339 if (array_key_exists($this->userId, self::$accessCodes))
340 {
341 return self::$accessCodes[$this->userId];
342 }
343
344 self::$accessCodes[$this->userId] = [];
345
346 $accessCodes = \CAccess::GetUserCodesArray($this->userId);
347 foreach ($accessCodes as $code)
348 {
349 self::$accessCodes[$this->userId][] = $code;
350 $signature = (new AccessCode($code))->getSignature();
351 if (
352 $signature
353 && $signature !== $code
354 )
355 {
356 self::$accessCodes[$this->userId][] = $signature;
357 }
358 }
359
360 return self::$accessCodes[$this->userId];
361 }
362
371 private function getLogId(string $typeId, int $entityId): ?int
372 {
373 $log = LogTable::getList([
374 'select' => ['ID'],
375 'filter' => [
376 '=RATING_ENTITY_ID' => $entityId,
377 '=RATING_TYPE_ID' => $typeId,
378 ],
379 'limit' => 1,
380 ])->fetch();
381
382 if (!$log)
383 {
384 return null;
385 }
386
387 return (int) $log['ID'];
388 }
389
395 private function isExtranetUser(int $userId): bool
396 {
397 if (!Loader::includeModule('extranet'))
398 {
399 return false;
400 }
401
402 return !\CExtranet::IsIntranetUser(SITE_ID, $userId);
403 }
404}
static getList(array $parameters=array())
static afterGetVoteList(array $param, array $items)