1C-Bitrix 25.700.0
Загрузка...
Поиск...
Не найдено
app.php
См. документацию.
1<?php
2namespace Bitrix\Rest;
3
4use Bitrix\Main;
5use Bitrix\Main\ArgumentException;
6use Bitrix\Main\Data\Cache;
7use Bitrix\Main\Engine\CurrentUser;
8use Bitrix\Main\Event;
9use Bitrix\Main\EventManager;
10use Bitrix\Main\EventResult;
11use Bitrix\Main\Localization\Loc;
12use Bitrix\Main\ObjectPropertyException;
13use Bitrix\Main\SystemException;
14use Bitrix\Main\Web\HttpClient;
15use Bitrix\Main\Web\Uri;
16use Bitrix\Rest\Engine\Access;
17use Bitrix\Rest\Event\Sender;
18use Bitrix\Rest\FormConfig\EventType;
19use Bitrix\Rest\Internals\FreeAppTable;
20use Bitrix\Rest\Marketplace\Client;
21use Bitrix\Main\ORM\Fields\BooleanField;
22use Bitrix\Main\ORM\Fields\Relations\OneToMany;
23use Bitrix\Rest\Preset\EventController;
24
25Loc::loadMessages(__FILE__);
26
27
67class AppTable extends Main\Entity\DataManager
68{
69 const ACTIVE = 'Y';
70 const INACTIVE = 'N';
71 const INSTALLED = 'Y';
72 const NOT_INSTALLED = 'N';
73 const TRIALED = 'Y';
74 const NOT_TRIALED = 'N';
75
76 const TYPE_STANDARD = 'N';
77 const TYPE_ONLY_API = 'A';
78 const TYPE_CONFIGURATION = 'C';
79 const TYPE_SMART_ROBOTS = 'R';
80 const TYPE_BIC_DASHBOARD = 'B';
81
82 const MODE_SITE = 'S';
83
84 const STATUS_LOCAL = 'L';
85 const STATUS_FREE = 'F';
86 const STATUS_PAID = 'P';
87 const STATUS_DEMO = 'D';
88 const STATUS_TRIAL = 'T';
90
92 const PAID_GRACE_PERIOD = -14;
93
94 const CACHE_TTL = 86400;
95 const CACHE_PATH = '/rest/app/';
96
97 private static $skipRemoteUpdate = false;
98
99 protected static $licenseLang = null;
100
101 protected static $applicationCache = array();
102
103 protected static $localAppDeniedScope = array(
104 'landing_cloud', 'rating',
105 );
106
112 public static function getTableName()
113 {
114 return 'b_rest_app';
115 }
116
122 public static function getMap()
123 {
124 return array(
125 'ID' => array(
126 'data_type' => 'integer',
127 'primary' => true,
128 'autocomplete' => true,
129 ),
130 'CLIENT_ID' => array(
131 'data_type' => 'string',
132 'required' => true,
133 'validation' => array(__CLASS__, 'validateClientId'),
134 ),
135 'CODE' => array(
136 'data_type' => 'string',
137 'required' => true,
138 'validation' => array(__CLASS__, 'validateCode'),
139 ),
140 'ACTIVE' => array(
141 'data_type' => 'boolean',
142 'values' => array(static::INACTIVE, static::ACTIVE),
143 ),
144 'INSTALLED' => array(
145 'data_type' => 'boolean',
146 'values' => array(static::NOT_INSTALLED, static::INSTALLED),
147 ),
148 'URL' => array(
149 'data_type' => 'string',
150 'validation' => array(__CLASS__, 'validateUrl'),
151 ),
152 'URL_DEMO' => array(
153 'data_type' => 'string',
154 'validation' => array(__CLASS__, 'validateUrlDemo'),
155 ),
156 'URL_INSTALL' => array(
157 'data_type' => 'string',
158 'validation' => array(__CLASS__, 'validateUrlInstall'),
159 ),
160 'URL_SETTINGS' => array(
161 'data_type' => 'string',
162 'validation' => array(__CLASS__, 'validateUrl'),
163 ),
164 'VERSION' => array(
165 'data_type' => 'string',
166 'validation' => array(__CLASS__, 'validateVersion'),
167 ),
168 'SCOPE' => array(
169 'data_type' => 'string',
170 'required' => true,
171 'validation' => array(__CLASS__, 'validateScope'),
172 ),
173 'STATUS' => array(
174 'data_type' => 'enum',
175 'required' => true,
176 'values' => array(
177 static::STATUS_LOCAL,
178 static::STATUS_FREE,
179 static::STATUS_PAID,
180 static::STATUS_DEMO,
181 static::STATUS_TRIAL,
182 static::STATUS_SUBSCRIPTION,
183 ),
184 ),
185 'DATE_FINISH' => array(
186 'data_type' => 'date',
187 ),
188 'IS_TRIALED' => array(
189 'data_type' => 'boolean',
190 'values' => array(static::NOT_TRIALED, static::TRIALED),
191 ),
192 'SHARED_KEY' => array(
193 'data_type' => 'string',
194 'validation' => array(__CLASS__, 'validateSharedKey'),
195 ),
196 'CLIENT_SECRET' => array(
197 'data_type' => 'string',
198 'validation' => array(__CLASS__, 'validateClientSecret'),
199 ),
200 'APP_NAME' => array(
201 'data_type' => 'string',
202 'validation' => array(__CLASS__, 'validateAppName'),
203 ),
204 'ACCESS' => array(
205 'data_type' => 'string',
206 'validation' => array(__CLASS__, 'validateAccess'),
207 ),
208 'APPLICATION_TOKEN' => array(
209 'data_type' => 'string',
210 ),
211 'MOBILE' => array(
212 'data_type' => 'boolean',
213 'values' => array(static::INACTIVE, static::ACTIVE),
214 ),
215 'USER_INSTALL' => array(
216 'data_type' => 'boolean',
217 'values' => array(static::INACTIVE, static::ACTIVE),
218 ),
219 'LANG' => array(
220 'data_type' => 'Bitrix\Rest\AppLangTable',
221 'reference' => array(
222 '=this.ID' => 'ref.APP_ID',
223 '=ref.LANGUAGE_ID' => new Main\DB\SqlExpression('?s', LANGUAGE_ID),
224 ),
225 ),
226 'LANG_DEFAULT' => array(
227 'data_type' => 'Bitrix\Rest\AppLangTable',
228 'reference' => array(
229 '=this.ID' => 'ref.APP_ID',
230 '=ref.LANGUAGE_ID' => new Main\DB\SqlExpression('?s', Loc::getDefaultLang(LANGUAGE_ID)),
231 ),
232 ),
233 'LANG_LICENSE' => array(
234 'data_type' => 'Bitrix\Rest\AppLangTable',
235 'reference' => array(
236 '=this.ID' => 'ref.APP_ID',
237 '=ref.LANGUAGE_ID' => new Main\DB\SqlExpression('?s', static::getLicenseLanguage()),
238 ),
239 ),
240 (new OneToMany('LANG_ALL', AppLangTable::class, 'APP'))
241 ->configureJoinType('left'),
243 'FREE_APP',
244 FreeAppTable::class,
245 Main\ORM\Query\Join::on('this.CODE', 'ref.APP_CODE'),
246 ),
248 'IS_FREE',
249 'CASE WHEN %s IS NOT NULL THEN 1 ELSE 0 END',
250 ['FREE_APP.APP_CODE'],
251 ),
252 );
253 }
254
260 public static function setSkipRemoteUpdate($v)
261 {
262 static::$skipRemoteUpdate = $v;
263 }
264
271 public static function onBeforeAdd(Main\Entity\Event $event)
272 {
273 $result = new Main\Entity\EventResult();
274 $data = $event->getParameters();
275
276 if($data['fields']['STATUS'] == static::STATUS_LOCAL && !$data['fields']['CLIENT_ID'])
277 {
279 $dummyClientId = 'no_client_id_'.$rnd;
280 $dummyClientSecret = 'no_client_secret_'.$rnd;
281
282 $result->modifyFields(array(
283 "CLIENT_ID" => $dummyClientId,
284 "CLIENT_SECRET" => $dummyClientSecret,
285 "CODE" => $dummyClientId,
286 ));
287 }
288
289 return $result;
290 }
291
299 public static function onAfterAdd(Main\Entity\Event $event)
300 {
301 Main\Application::getInstance()->getCache()->cleanDir('rest/market_subscription');
302 EventController::onAddApp($event);
303 $data = $event->getParameters();
304 if(!static::$skipRemoteUpdate)
305 {
306 if(
307 $data['fields']['STATUS'] === static::STATUS_LOCAL
308 && OAuthService::getEngine()->isRegistered()
309 )
310 {
311 try
312 {
313 $appFields = array(
314 'TITLE' => $data['fields']['APP_NAME'],
315 'REDIRECT_URI' => $data['fields']['URL'],
316 'SCOPE' => $data['fields']['SCOPE'],
317 );
318
319 $clientData = OAuthService::getEngine()
320 ->getClient()
321 ->addApplication($appFields);
322 }
323 catch(Main\SystemException $e)
324 {
325 $clientData = array(
326 "error" => $e->getCode(),
327 "error_description" => $e->getMessage(),
328 );
329 }
330
331 if(is_array($clientData))
332 {
333 if($clientData['result'])
334 {
335 static::$skipRemoteUpdate = true;
336
337 static::clearClientCache($clientData['result']['client_id']);
338
339 $updateResult = static::update($data['id'], array(
340 'CLIENT_ID' => $clientData['result']['client_id'],
341 'CLIENT_SECRET' => $clientData['result']['client_secret'],
342 'STATUS' => static::STATUS_LOCAL,
343 'SHARED_KEY' => md5(\CRestUtil::getMemberId().$clientData['result']['client_secret']),
344 'CODE' => $clientData['result']['client_id'],
345 ));
346 static::$skipRemoteUpdate = false;
347
348 if($updateResult->isSuccess())
349 {
350 return true;
351 }
352 else
353 {
354 $clientData = array('error' => $updateResult->getErrorMessages());
355 }
356 }
357 }
358 else
359 {
360 $clientData = array('error' => 'Unknown error');
361 }
362
363 static::$skipRemoteUpdate = true;
364 static::delete($data['id']);
365 static::$skipRemoteUpdate = false;
366
367 throw new OAuthException($clientData);
368 }
369 }
370
371 if($data['fields']['STATUS'] !== static::STATUS_LOCAL)
372 {
373 \Bitrix\Rest\Engine\Access::getActiveEntity(true);
374 }
375
376 return true;
377 }
378
386 public static function onAfterUpdate(Main\Entity\Event $event)
387 {
388 Main\Application::getInstance()->getCache()->cleanDir('rest/market_subscription');
389 $data = $event->getParameters();
390 static::clearClientCache($data['primary']['ID']);
391
392 if(!static::$skipRemoteUpdate)
393 {
394 if(
395 isset($data['fields']['STATUS'])
396 && $data['fields']['STATUS'] === static::STATUS_LOCAL
397 && OAuthService::getEngine()->isRegistered()
398 )
399 {
400 $app = static::getByClientId($data['primary']['ID']);
401
402 try
403 {
404 $updateResult = OAuthService::getEngine()
405 ->getClient()
406 ->updateApplication(array(
407 "CLIENT_ID" => $app['CLIENT_ID'],
408 'TITLE' => $data['fields']['APP_NAME'],
409 'REDIRECT_URI' => $data['fields']['URL'],
410 'SCOPE' => $data['fields']['SCOPE'],
411 ));
412
413 if($updateResult['result'])
414 {
415 return true;
416 }
417 }
418 catch(Main\SystemException $e)
419 {
420 $updateResult = array(
421 "error" => $e->getCode(),
422 "error_description" => $e->getMessage(),
423 );
424 }
425
426 throw new OAuthException($updateResult);
427 }
428 }
429
430 if(isset($data['fields']['STATUS']) && $data['fields']['STATUS'] !== static::STATUS_LOCAL)
431 {
432 \Bitrix\Rest\Engine\Access::getActiveEntity(true);
433 }
434
435 return true;
436 }
437
443 public static function onDelete(Main\Entity\Event $event)
444 {
445 if(!static::$skipRemoteUpdate)
446 {
447 $data = $event->getParameters();
448 $app = static::getByClientId($data['primary']['ID']);
449
450 if($app['STATUS'] == AppTable::STATUS_LOCAL)
451 {
452 if(OAuthService::getEngine()->isRegistered())
453 {
454 \CRestUtil::cleanApp($app["ID"], true);
455
456 try
457 {
459 ->getClient()
460 ->deleteApplication(array(
461 'CLIENT_ID' => $app['CLIENT_ID'],
462 ));
463 }
464 catch(\Bitrix\Main\SystemException $e)
465 {
466 }
467 }
468 }
469 }
470 }
471
477 public static function onAfterDelete(Main\Entity\Event $event)
478 {
479 Main\Application::getInstance()->getCache()->cleanDir('rest/market_subscription');
480 $data = $event->getParameters();
481
482 static::clearClientCache($data['primary']['ID']);
483 AppLangTable::deleteByApp($data['primary']['ID']);
484 }
485
486 public static function isInstalled(int $appId): bool
487 {
488 $row = self::getRowById($appId);
489 if (!$row)
490 {
491 return false;
492 }
493
494 return $row['INSTALLED'] === self::INSTALLED;
495 }
496
497 public static function install($appId)
498 {
499 $appInfo = static::getByClientId($appId);
500 if($appInfo)
501 {
502 $eventFields = array(
503 'APP_ID' => $appId,
504 'VERSION' => $appInfo['VERSION'],
505 'ACTIVE' => $appInfo['ACTIVE'],
506 'INSTALLED' => $appInfo['INSTALLED'],
507 );
508
509 if ($appInfo['ACTIVE'] === self::ACTIVE && $appInfo['INSTALLED'] === self::INSTALLED)
510 {
511 $res = PlacementTable::getList(
512 [
513 'filter' => [
514 '=APP_ID' => $appInfo['ID'],
515 ],
516 'select' => [
517 'ID',
518 'PLACEMENT',
519 'USER_ID',
520 ],
521 ]
522 );
523 while ($item = $res->fetch())
524 {
525 $event = new Event(
526 'rest',
528 [
529 'ID' => $item['ID'],
530 'PLACEMENT' => $item['PLACEMENT'],
531 'USER_ID' => $item['USER_ID'],
532 ]
533 );
534 EventManager::getInstance()->send($event);
535 }
536 }
537
538 foreach(GetModuleEvents("rest", "OnRestAppInstall", true) as $eventHandler)
539 {
540 ExecuteModuleEventEx($eventHandler, array($eventFields));
541 }
542 }
543 }
544
551 public static function uninstall($appId, $clean = 0)
552 {
553 $appInfo = static::getByClientId($appId);
554 if($appInfo)
555 {
556 \CRestUtil::cleanApp($appId, $clean);
557
558 if($appInfo['STATUS'] !== static::STATUS_LOCAL)
559 {
560 OAuthService::getEngine()->getClient()->unInstallApplication(array(
561 'CLIENT_ID' => $appInfo['CLIENT_ID']
562 ));
563 }
564 }
565 }
566
574 public static function checkUninstallAvailability($appId, $clean = 0)
575 {
576 $event = new Main\Event('rest', 'onBeforeApplicationUninstall', [
577 'ID' => $appId,
578 'CLEAN' => $clean
579 ]);
580 $event->send();
581
583 if ($event->getResults())
584 {
586 foreach ($event->getResults() as $eventResult)
587 {
588 if($eventResult->getType() === EventResult::ERROR)
589 {
590 $eventResultData = $eventResult->getParameters();
591 if ($eventResultData instanceof Main\Error)
592 {
593 $result->add([$eventResultData]);
594 }
595 }
596 }
597 }
598
599 return $result;
600 }
601
609 public static function updateAppStatusInfo()
610 {
611 $appList = OAuthService::getEngine()->getClient()->getApplicationList();
612
613 if(is_array($appList) && is_array($appList['result']))
614 {
615 $dbApps = static::getList(array(
616 'filter' => array(
617 '!=STATUS' => static::STATUS_LOCAL,
618 ),
619 'select' => array(
620 'ID', 'CLIENT_ID', 'STATUS', 'DATE_FINISH',
621 )
622 ));
623
624 $localApps = array();
625 while($app = $dbApps->fetch())
626 {
627 $localApps[$app['CLIENT_ID']] = $app;
628 }
629
630 foreach($appList['result'] as $app)
631 {
632 if(array_key_exists($app['client_id'], $localApps))
633 {
634 $dateFinishLocal = $localApps[$app['client_id']]['DATE_FINISH']
635 ? $localApps[$app['client_id']]['DATE_FINISH']->getTimestamp()
636 : '';
637 $dateFinishRemote = ($app['date_finish'] ?? null) ? Main\Type\Date::createFromTimestamp($app['date_finish'])->getTimestamp() : '';
638
639 if(
640 $localApps[$app['client_id']]['STATUS'] !== $app['status']
641 || $dateFinishRemote != $dateFinishLocal
642 )
643 {
644 $appFields = array(
645 'STATUS' => $app['status'],
646 'DATE_FINISH' => $app['date_finish']
647 ? Main\Type\Date::createFromTimestamp($app['date_finish'])
648 : '',
649 );
650
651 static::setSkipRemoteUpdate(true);
652 $result = static::update($localApps[$app['client_id']]['ID'], $appFields);
653 static::setSkipRemoteUpdate(false);
654
655 if(
656 $result->isSuccess()
657 && $appFields['STATUS'] === static::STATUS_PAID
658 )
659 {
660 static::callAppPaymentEvent($localApps[$app['client_id']]['ID']);
661 }
662 }
663 }
664 else
665 {
666 $appFields = array(
667 'CLIENT_ID' => $app['client_id'],
668 'CODE' => $app['code'],
669 'ACTIVE' => $app['active'] ? static::ACTIVE : static::INACTIVE,
670 'INSTALLED' => static::NOT_INSTALLED,
671 'VERSION' => $app['version'],
672 'STATUS' => $app['status'],
673 'SCOPE' => $app['scope'],
674 );
675
676 if(!empty($app['date_finish']))
677 {
678 $appFields['DATE_FINISH'] = Main\Type\Date::createFromTimestamp($app['date_finish']);
679 }
680
681 $result = static::add($appFields);
682
683 if($result->isSuccess() && $appFields['STATUS'] === static::STATUS_PAID)
684 {
685 static::callAppPaymentEvent($result->getId());
686 }
687 }
688 }
689 }
690 }
691
697 public static function callAppPaymentEvent($appId)
698 {
699 // for compatibility purpose module_id is bitrix24 here
700 foreach(GetModuleEvents('bitrix24', 'OnAfterAppPaid', true) as $event)
701 {
703 }
704 }
705
713 public static function getAppStatusInfo($app, $detailUrl)
714 {
715 $res = array();
716
717 if (
718 !empty($app)
719 && (
720 is_string($app)
721 || is_integer($app)
722 )
723 )
724 {
725 $appInfo = $app = static::getByClientId($app);
726 }
727 elseif (isset($app['CODE']))
728 {
729 $appInfo = static::getByClientId($app['CODE']);
730 }
731
732 if(is_array($app))
733 {
734 $res['STATUS'] = $app['STATUS'];
735 $res['PAYMENT_NOTIFY'] = 'N';
736 $res['PAYMENT_EXPIRED'] = 'N';
737 $res['PAYMENT_ALLOW'] = 'Y';
738
739 if ($app['STATUS'] === self::STATUS_SUBSCRIPTION)
740 {
741 if (!\Bitrix\Rest\Marketplace\Client::isSubscriptionAvailable())
742 {
743 $res['MESSAGE_REPLACE'] = array(
744 '#DETAIL_URL#' => $detailUrl,
745 '#DAYS#' => 0,
746 '#CODE#' => urlencode($app['CODE'])
747 );
748 $res['PAYMENT_NOTIFY'] = 'Y';
749 $res['PAYMENT_EXPIRED'] = 'Y';
750 $res['PAYMENT_ALLOW'] = 'N';
751 }
752 else
753 {
755 if (!is_null($dateFinish))
756 {
757 $res['DAYS_LEFT'] = floor(($dateFinish->getTimestamp() - \CTimeZone::getOffset() - time()) / 86400);
758 if($res['DAYS_LEFT'] < 0)
759 {
760 $res['MESSAGE_REPLACE'] = array(
761 '#DETAIL_URL#' => $detailUrl,
762 '#DAYS#' => $res['DAYS_LEFT'],
763 '#CODE#' => urlencode($app['CODE'])
764 );
765 $res['PAYMENT_NOTIFY'] = 'Y';
766 $res['PAYMENT_EXPIRED'] = 'Y';
767 $res['PAYMENT_ALLOW'] = 'N';
768 }
769 elseif ($res['DAYS_LEFT'] < static::PAID_NOTIFY_DAYS)
770 {
771 $res['MESSAGE_REPLACE'] = array(
772 '#DETAIL_URL#' => $detailUrl,
773 '#DAYS#' => $res['DAYS_LEFT'],
774 '#CODE#' => urlencode($app['CODE'])
775 );
776 $res['PAYMENT_NOTIFY'] = 'Y';
777 }
778 }
779 }
780 }
781 elseif($app['DATE_FINISH'] <> '' && $app['STATUS'] != self::STATUS_FREE)
782 {
783 $res['DAYS_LEFT'] = floor(
784 (MakeTimeStamp($app['DATE_FINISH']) - \CTimeZone::getOffset() - time()) / 86400
785 );
786
787 if(
788 $res['DAYS_LEFT'] < static::PAID_NOTIFY_DAYS
789 || $app['STATUS'] == static::STATUS_TRIAL)
790 {
791 $res['PAYMENT_NOTIFY'] = 'Y';
792
793 if($res['DAYS_LEFT'] < 0)
794 {
795 $res['PAYMENT_EXPIRED'] = 'Y';
796
797 if($app['STATUS'] == static::STATUS_TRIAL)
798 {
799 $res['PAYMENT_ALLOW'] = 'N';
800 }
801 elseif(
802 $app['STATUS'] == static::STATUS_PAID
803 && $res['DAYS_LEFT'] < static::PAID_GRACE_PERIOD
804 )
805 {
806 if($app['IS_TRIALED'] == 'N' && $app['URL_DEMO'] <> '')
807 {
808 $res['STATUS'] = static::STATUS_DEMO;
809 }
810 else
811 {
812 $res['PAYMENT_ALLOW'] = 'N';
813 }
814 }
815 }
816 }
817
818 $res['MESSAGE_REPLACE'] = array(
819 "#DETAIL_URL#" => $detailUrl,
820 "#DAYS#" => $res['DAYS_LEFT'],
821 "#CODE#" => urlencode($app['CODE']),
822 );
823 }
824 elseif($app['STATUS'] == self::STATUS_DEMO)
825 {
826 $res['PAYMENT_NOTIFY'] = 'Y';
827 $res['MESSAGE_REPLACE'] = array(
828 "#DETAIL_URL#" => $detailUrl,
829 "#CODE#" => urlencode($app['CODE'])
830 );
831 }
832 else
833 {
834 $res['MESSAGE_REPLACE'] = array(
835 "#DETAIL_URL#" => $detailUrl,
836 "#CODE#" => urlencode($app['CODE'])
837 );
838 }
839
840 $res['MESSAGE_SUFFIX'] = '_'.$res['STATUS'].'_'.$res['PAYMENT_EXPIRED'].'_'.$res['PAYMENT_ALLOW'];
841
842 }
843
844 if (!empty($appInfo['CLIENT_ID']))
845 {
847 \Bitrix\Rest\Engine\Access\HoldEntity::TYPE_APP,
848 $appInfo['CLIENT_ID']
849 );
850 if ($isHold)
851 {
852 $res['MESSAGE_SUFFIX'] = '_HOLD_OVERLOAD';
853 $res['PAYMENT_NOTIFY'] = 'Y';
854 }
855 }
856
857 return $res;
858 }
859
870 public static function getStatusMessage($suffix, $replace = null, $checkAdmin = true, $language = null)
871 {
872 if ($checkAdmin && \CRestUtil::isAdmin())
873 {
874 $suffix .= '_A';
875 }
876
877 if (
878 is_array($replace)
879 && array_key_exists('#DAYS#', $replace)
880 && (
881 is_int($replace['#DAYS#'])
882 || preg_match('/^(-|)\d+$/', $replace['#DAYS#'])
883 )
884 )
885 {
886 $replace['#DAYS#'] = FormatDate('ddiff', time(), time() + 24 * 60 * 60 * $replace['#DAYS#']);
887 }
888
889 return Loc::getMessage('PAYMENT_MESSAGE' . $suffix, $replace, $language);
890 }
891
896 public static function getAccess($appId)
897 {
898 $appInfo = static::getByClientId($appId);
899 if($appInfo)
900 {
901 if($appInfo['ACCESS'] <> '')
902 {
903 $rightsList = explode(",", $appInfo["ACCESS"]);
904
905 $access = new \CAccess();
906 $accessNames = $access->getNames($rightsList);
907
908 $result = array();
909 foreach($rightsList as $right)
910 {
912 "id" => $right,
913 "provider" => $accessNames[$right]["provider_id"],
914 "name" => $accessNames[$right]["name"]
915 );
916 }
917 return $result;
918 }
919 }
920
921 return false;
922 }
923
929 public static function setAccess($appId, $newRights = array())
930 {
931 $appInfo = static::getByClientId($appId);
932 if($appInfo)
933 {
934 $rights = '';
935 if(is_array($newRights) && !empty($newRights))
936 {
937 $rightIdList = array();
938 foreach($newRights as $key => $rightsList)
939 {
940 foreach($rightsList as $rightId => $ar)
941 {
942 $rightIdList[] = $rightId;
943 }
944 }
945 $rights = implode(",", $rightIdList);
946 }
947
948 static::update($appId, array(
949 'ACCESS' => $rights,
950 ));
951 }
952
953 if(defined("BX_COMP_MANAGED_CACHE"))
954 {
955 global $CACHE_MANAGER;
956 $CACHE_MANAGER->ClearByTag('bitrix24_left_menu');
957 }
958 }
959
967 public static function getByClientId($clientId)
968 {
969 if(!array_key_exists($clientId, static::$applicationCache))
970 {
971 if(strval(intval($clientId)) == $clientId)
972 {
973 $filter = array('=ID' => $clientId);
974 }
975 else
976 {
977 $filter = array(
978 array(
979 'LOGIC' => 'OR',
980 '=CODE' => $clientId,
981 '=CLIENT_ID' => $clientId,
982 ),
983 );
984 }
985
986 $dbRes = static::getList(
987 [
988 'filter' => $filter,
989 'select' => [
990 '*',
991 'MENU_NAME' => 'LANG.MENU_NAME',
992 'MENU_NAME_DEFAULT' => 'LANG_DEFAULT.MENU_NAME',
993 'MENU_NAME_LICENSE' => 'LANG_LICENSE.MENU_NAME',
994 ],
995 'limit' => 1,
996 ]
997 );
998
999 foreach ($dbRes->fetchCollection() as $app)
1000 {
1001 $appInfo = [
1002 'ID' => $app->getId(),
1003 'MENU_NAME' => !is_null($app->getLang()) ? $app->getLang()->getMenuName() : '',
1004 'MENU_NAME_DEFAULT' => !is_null($app->getLangDefault()) ? $app->getLangDefault()->getMenuName() : '',
1005 'MENU_NAME_LICENSE' => !is_null($app->getLangLicense()) ? $app->getLangLicense()->getMenuName() : '',
1006 ];
1007 foreach ($app->sysGetEntity()->getScalarFields() as $field)
1008 {
1009 $fieldName = $field->getName();
1010 if ($field instanceof BooleanField)
1011 {
1012 $appInfo[$fieldName] = $app->get($fieldName) ? 'Y' : 'N';
1013 }
1014 else
1015 {
1016 $appInfo[$fieldName] = $app->get($fieldName);
1017 }
1018 }
1019 $app->fillLangAll();
1020 if (!is_null($app->getLangAll()))
1021 {
1022 foreach ($app->getLangAll() as $lang)
1023 {
1024 $appInfo['LANG_ALL'][$lang->getLanguageId()] = [
1025 'MENU_NAME' => $lang->getMenuName(),
1026 ];
1027 }
1028 }
1029 if ($appInfo['MENU_NAME'] === '')
1030 {
1031 $appInfo = Lang::mergeFromLangAll($appInfo);
1032 }
1033 }
1034
1035 if (isset($appInfo) && is_array($appInfo))
1036 {
1037 static::$applicationCache[$appInfo['ID']] = $appInfo;
1038 static::$applicationCache[$appInfo['CLIENT_ID']] = $appInfo;
1039 static::$applicationCache[$appInfo['CODE']] = $appInfo;
1040 }
1041 }
1042
1043 return static::$applicationCache[$clientId] ?? null;
1044 }
1045
1046 protected static function clearClientCache($clientId)
1047 {
1048 if(array_key_exists($clientId, static::$applicationCache))
1049 {
1050 $app = static::$applicationCache[$clientId];
1051 if(is_array($app))
1052 {
1053 unset(static::$applicationCache[$app['ID']]);
1054 unset(static::$applicationCache[$app['CLIENT_ID']]);
1055 }
1056 else
1057 {
1058 unset(static::$applicationCache[$clientId]);
1059 }
1060 }
1061 }
1062
1063 protected static function getLicenseLanguage()
1064 {
1065 if(static::$licenseLang === null)
1066 {
1067 if(Main\Loader::includeModule('bitrix24'))
1068 {
1069 static::$licenseLang = \CBitrix24::getLicensePrefix();
1070 }
1071 else
1072 {
1073 $dbSites = \CSite::getList('sort', 'asc', array('DEFAULT' => 'Y', 'ACTIVE' => 'Y'));
1074 $site = $dbSites->fetch();
1075
1076 static::$licenseLang = is_array($site) && isset($site['LANGUAGE_ID']) ? $site['LANGUAGE_ID'] : LANGUAGE_ID;
1077 }
1078
1079 if(static::$licenseLang === null)
1080 {
1081 static::$licenseLang = 'en';
1082 }
1083 }
1084
1085 return static::$licenseLang;
1086 }
1087
1088
1094 public static function validateClientId()
1095 {
1096 return array(
1097 new Main\Entity\Validator\Length(null, 128),
1098 new Main\Entity\Validator\Unique(),
1099 );
1100 }
1101
1107 public static function validateCode()
1108 {
1109 return array(
1110 new Main\Entity\Validator\Length(null, 128),
1111 new Main\Entity\Validator\Unique(),
1112 );
1113 }
1114
1120 public static function validateUrl()
1121 {
1122 return array(
1123 new Main\Entity\Validator\Length(null, 1000),
1124 );
1125 }
1126
1132 public static function validateUrlDemo()
1133 {
1134 return array(
1135 new Main\Entity\Validator\Length(null, 1000),
1136 );
1137 }
1138
1144 public static function validateUrlInstall()
1145 {
1146 return array(
1147 new Main\Entity\Validator\Length(null, 1000),
1148 function ($value, $primary, array $row, Main\Entity\Field $field)
1149 {
1150 $checkResult = true;
1151
1152 if($value)
1153 {
1154 try
1155 {
1156 if(!HandlerHelper::checkCallback($value, $row, false))
1157 {
1158 $checkResult = false;
1159 }
1160 }
1161 catch(RestException $e)
1162 {
1163 $checkResult = false;
1164 }
1165
1166 if(!$checkResult)
1167 {
1168 return Loc::getMessage("MP_ERROR_INCORRECT_URL_INSTALL");
1169 }
1170 }
1171
1172 return true;
1173 }
1174 );
1175 }
1176
1182 public static function validateVersion()
1183 {
1184 return array(
1185 new Main\Entity\Validator\Length(null, 4),
1186 );
1187 }
1188
1194 public static function validateScope()
1195 {
1196 return array(
1197 new Main\Entity\Validator\Length(null, 2000),
1198 );
1199 }
1200
1206 public static function validateSharedKey()
1207 {
1208 return array(
1209 new Main\Entity\Validator\Length(null, 32),
1210 );
1211 }
1212
1218 public static function validateClientSecret()
1219 {
1220 return array(
1221 new Main\Entity\Validator\Length(null, 100),
1222 );
1223 }
1224
1230 public static function validateAppName()
1231 {
1232 return array(
1233 new Main\Entity\Validator\Length(null, 1000),
1234 );
1235 }
1236
1242 public static function validateAccess()
1243 {
1244 return array(
1245 new Main\Entity\Validator\Length(null, 2000),
1246 );
1247 }
1248
1253 public static function cleanLocalPermissionList(array $permissionList)
1254 {
1255 foreach($permissionList as $key => $perm)
1256 {
1257 if(in_array($perm, static::$localAppDeniedScope))
1258 {
1259 unset($permissionList[$key]);
1260 }
1261 }
1262
1263 return array_values($permissionList);
1264 }
1265
1271 public static function canUninstallByType($code, $version = false)
1272 {
1273 $result = true;
1274
1275 $type = static::getAppType($code, $version);
1276 if($type == static::TYPE_CONFIGURATION)
1277 {
1278 $appList = \Bitrix\Rest\Configuration\Helper::getInstance()->getBasicAppList();
1279 if(in_array($code, $appList))
1280 {
1281 $result = false;
1282 }
1283 }
1284
1285 return $result;
1286 }
1287
1293 public static function getAppType($code, $version = false)
1294 {
1295 $result = false;
1296 $cache = Cache::createInstance();
1297 if ($cache->initCache(static::CACHE_TTL, 'appType'.md5($code.$version), static::CACHE_PATH))
1298 {
1299 $result = $cache->getVars();
1300 }
1301 elseif ($cache->startDataCache())
1302 {
1303 $appDetailInfo = Client::getInstall($code, $version);
1304 $result = ($appDetailInfo['ITEMS']['TYPE'])?:false;
1305 $cache->endDataCache($result);
1306 }
1307
1308 return $result;
1309 }
1310}
1311
1312class App
1313{
1314 public function __construct(
1315 private string $clientId
1316 )
1317 {
1318 }
1319
1325 public function fetchAppFormConfig(array $formData, EventType $type): string
1326 {
1327 $appData = AppTable::getByClientId($this->clientId);
1328 if (empty($appData['URL_SETTINGS']))
1329 {
1330 throw new ArgumentException('Property "URL_SETTINGS" is empty', 'URL_SETTINGS');
1331 }
1332 $uri = new Uri($appData['URL_SETTINGS']);
1333 $httpClient = new HttpClient();
1334 $params = Sender::getDefaultEventParams();
1335 $params['sendRefreshToken'] = true;
1336 $event = [
1337 'event' => $type->value,
1338 'data' => $formData,
1339 'auth' => Sender::getAuth(
1340 $this->clientId,
1341 CurrentUser::get()->getId() ?? 0,
1342 [],
1343 $params
1344 )
1345 ];
1346
1347 return $httpClient->post($uri, $event);
1348 }
1349}
$type
Определения options.php:106
$dbSites
Определения options.php:14
static getInstance()
Определения application.php:98
Определения error.php:15
Определения event.php:5
static getString($length, $caseSensitive=false)
Определения random.php:76
static createFromTimestamp($timestamp)
Определения date.php:402
Определения uri.php:17
Определения app.php:1313
fetchAppFormConfig(array $formData, EventType $type)
Определения app.php:1325
__construct(private string $clientId)
Определения app.php:1314
static deleteByApp($appId)
Определения applang.php:78
Определения app.php:68
static validateClientId()
Определения app.php:1094
static getStatusMessage($suffix, $replace=null, $checkAdmin=true, $language=null)
Определения app.php:870
static validateUrl()
Определения app.php:1120
const TYPE_SMART_ROBOTS
Определения app.php:79
static isInstalled(int $appId)
Определения app.php:486
const STATUS_PAID
Определения app.php:86
const NOT_TRIALED
Определения app.php:74
static getMap()
Определения app.php:122
const CACHE_PATH
Определения app.php:95
static canUninstallByType($code, $version=false)
Определения app.php:1271
static validateScope()
Определения app.php:1194
static getAppType($code, $version=false)
Определения app.php:1293
static getAppStatusInfo($app, $detailUrl)
Определения app.php:713
static onBeforeAdd(Main\Entity\Event $event)
Определения app.php:271
static clearClientCache($clientId)
Определения app.php:1046
static validateAccess()
Определения app.php:1242
static onAfterDelete(Main\Entity\Event $event)
Определения app.php:477
static install($appId)
Определения app.php:497
const INSTALLED
Определения app.php:71
const TRIALED
Определения app.php:73
static validateUrlInstall()
Определения app.php:1144
static getByClientId($clientId)
Определения app.php:967
const TYPE_CONFIGURATION
Определения app.php:78
static validateAppName()
Определения app.php:1230
const PAID_GRACE_PERIOD
Определения app.php:92
static $localAppDeniedScope
Определения app.php:103
const TYPE_BIC_DASHBOARD
Определения app.php:80
const STATUS_TRIAL
Определения app.php:88
const TYPE_STANDARD
Определения app.php:76
static $licenseLang
Определения app.php:99
const STATUS_LOCAL
Определения app.php:84
static uninstall($appId, $clean=0)
Определения app.php:551
static onDelete(Main\Entity\Event $event)
Определения app.php:443
static validateUrlDemo()
Определения app.php:1132
const PAID_NOTIFY_DAYS
Определения app.php:91
const ACTIVE
Определения app.php:69
static getLicenseLanguage()
Определения app.php:1063
const STATUS_DEMO
Определения app.php:87
static getAccess($appId)
Определения app.php:896
static onAfterUpdate(Main\Entity\Event $event)
Определения app.php:386
const MODE_SITE
Определения app.php:82
const NOT_INSTALLED
Определения app.php:72
static $applicationCache
Определения app.php:101
const CACHE_TTL
Определения app.php:94
static cleanLocalPermissionList(array $permissionList)
Определения app.php:1253
static validateSharedKey()
Определения app.php:1206
const STATUS_FREE
Определения app.php:85
static setAccess($appId, $newRights=array())
Определения app.php:929
const STATUS_SUBSCRIPTION
Определения app.php:89
const INACTIVE
Определения app.php:70
static onAfterAdd(Main\Entity\Event $event)
Определения app.php:299
static setSkipRemoteUpdate($v)
Определения app.php:260
const TYPE_ONLY_API
Определения app.php:77
static updateAppStatusInfo()
Определения app.php:609
static callAppPaymentEvent($appId)
Определения app.php:697
static validateVersion()
Определения app.php:1182
static validateClientSecret()
Определения app.php:1218
static getTableName()
Определения app.php:112
static validateCode()
Определения app.php:1107
static getInstance()
Определения helper.php:49
static is(string $type, string $code)
Определения holdentity.php:169
static checkCallback($handlerUrl, $appInfo=array(), $checkInstallUrl=true)
Определения handlerhelper.php:31
static mergeFromLangAll($data)
Определения lang.php:59
static getSubscriptionFinalDate()
Определения client.php:594
static getEngine()
Определения oauthservice.php:49
const PREFIX_EVENT_ON_AFTER_ADD
Определения placement.php:46
global $CACHE_MANAGER
Определения clear_component_cache.php:7
$right
Определения options.php:8
$data['IS_AVAILABLE']
Определения .description.php:13
</td ></tr ></table ></td ></tr >< tr >< td class="bx-popup-label bx-width30"><?=GetMessage("PAGE_NEW_TAGS")?> array( $site)
Определения file_new.php:804
$res
Определения filter_act.php:7
$perm
Определения options.php:169
$result
Определения get_property_values.php:14
$filter
Определения iblock_catalog_list.php:54
$app
Определения proxy.php:8
if(!is_null($config))($config as $configItem)(! $configItem->isVisible()) $code
Определения options.php:195
if(file_exists($_SERVER['DOCUMENT_ROOT'] . "/urlrewrite.php")) $uri
Определения urlrewrite.php:61
if(!defined('SITE_ID')) $lang
Определения include.php:91
if(!is_array($deviceNotifyCodes)) $access
Определения options.php:174
ExecuteModuleEventEx($arEvent, $arParams=[])
Определения tools.php:5214
FormatDate($format="", $timestamp=false, $now=false, ?string $languageId=null)
Определения tools.php:871
GetModuleEvents($MODULE_ID, $MESSAGE_ID, $bReturnArray=false)
Определения tools.php:5177
MakeTimeStamp($datetime, $format=false)
Определения tools.php:538
Определения accesscode.php:9
Определения arrayresult.php:2
Определения action.php:3
Определения ufield.php:9
Определения chain.php:3
Определения handlers.php:8
Определения collection.php:2
Определения buffer.php:3
EventType
Определения EventType.php:6
$event
Определения prolog_after.php:141
if( $daysToExpire >=0 &&$daysToExpire< 60 elseif)( $daysToExpire< 0)
Определения prolog_main_admin.php:393
$ar
Определения options.php:199
if(empty($signedUserToken)) $key
Определения quickway.php:257
if($inWords) echo htmlspecialcharsbx(Number2Word_Rus(roundEx($totalVatSum $params['CURRENCY']
Определения template.php:799
$clientId
Определения seo_client.php:18
$rights
Определения options.php:4
$dbRes
Определения yandex_detail.php:168
$site
Определения yandex_run.php:614