3namespace Bitrix\Socialnetwork\Integration\UI\EntitySelector;
5use Bitrix\Intranet\Settings\Tools\ToolsManager;
6use Bitrix\Main\Application;
7use Bitrix\Main\Config\Option;
8use Bitrix\Main\ORM\Fields\BooleanField;
10use Bitrix\Main\Localization\Loc;
11use Bitrix\Main\ModuleManager;
12use Bitrix\Main\ORM\Fields\ExpressionField;
13use Bitrix\Main\ORM\Fields\IntegerField;
14use Bitrix\Main\ORM\Fields\Relations\Reference;
15use Bitrix\Main\ORM\Query\Filter;
16use Bitrix\Main\ORM\Query\Join;
17use Bitrix\Main\ORM\Query\Query;
18use Bitrix\Main\Search\Content;
19use Bitrix\Socialnetwork\Collab\CollabFeature;
20use Bitrix\Socialnetwork\Collab\Control\Option\Type\WhoCanInviteOption;
21use Bitrix\Socialnetwork\Collab\Integration\IM;
22use Bitrix\Socialnetwork\Collab\Internals\CollabOptionTable;
23use Bitrix\Socialnetwork\EO_Workgroup;
24use Bitrix\Socialnetwork\EO_Workgroup_Collection;
25use Bitrix\Socialnetwork\FeaturePermTable;
26use Bitrix\Socialnetwork\FeatureTable;
27use Bitrix\Socialnetwork\Helper\Feature;
28use Bitrix\Socialnetwork\Integration\Im\Chat\Workgroup;
29use Bitrix\Socialnetwork\UserToGroupTable;
30use Bitrix\Socialnetwork\WorkgroupSiteTable;
31use Bitrix\Socialnetwork\WorkgroupTable;
32use Bitrix\Socialnetwork\WorkgroupViewTable;
33use Bitrix\UI\EntitySelector\BaseProvider;
34use Bitrix\UI\EntitySelector\Dialog;
35use Bitrix\UI\EntitySelector\Item;
36use Bitrix\UI\EntitySelector\RecentItem;
37use Bitrix\UI\EntitySelector\SearchQuery;
38use Bitrix\UI\EntitySelector\Tab;
39use Bitrix\Socialnetwork\Item\Workgroup\Type;
40use Bitrix\Socialnetwork\Collab\User\User;
48 private static array $groupDialogIds = [];
52 parent::__construct();
56 $this->options[
'project'] =
$options[
'project'];
61 $this->options[
'!type'] =
$options[
'!type'];
66 $this->options[
'type'] =
$options[
'type'];
71 $this->options[
'extranet'] =
$options[
'extranet'];
76 $this->options[
'landing'] =
$options[
'landing'];
81 $this->options[
'features'] =
$options[
'features'];
84 $this->options[
'checkFeatureForCreate'] =
false;
85 if (isset(
$options[
'checkFeatureForCreate']) && is_bool(
$options[
'checkFeatureForCreate']))
87 $this->options[
'checkFeatureForCreate'] =
$options[
'checkFeatureForCreate'];
90 $this->options[
'fillRecentTab'] =
null;
93 $this->options[
'fillRecentTab'] =
$options[
'fillRecentTab'];
96 $this->options[
'createProjectLink'] =
null;
97 if (isset(
$options[
'createProjectLink']) && is_bool(
$options[
'createProjectLink']))
99 $this->options[
'createProjectLink'] =
$options[
'createProjectLink'];
102 $this->options[
'lockProjectLinkFeatureId'] =
'';
103 if (isset(
$options[
'lockProjectLinkFeatureId']) && is_string(
$options[
'lockProjectLinkFeatureId']))
105 $this->options[
'lockProjectLinkFeatureId'] =
$options[
'lockProjectLinkFeatureId'];
108 $this->options[
'lockProjectLink'] =
false;
109 if (isset(
$options[
'lockProjectLink']) && is_bool(
$options[
'lockProjectLink']))
111 $this->options[
'lockProjectLink'] =
$options[
'lockProjectLink'];
116 if (is_array(
$options[
'projectId']))
118 $this->options[
'projectId'] =
$options[
'projectId'];
122 $this->options[
'projectId'] = (int)
$options[
'projectId'];
127 if (is_array(
$options[
'!projectId']))
129 $this->options[
'!projectId'] =
$options[
'!projectId'];
133 $this->options[
'!projectId'] = (int)
$options[
'!projectId'];
137 $this->options[
'maxProjectsInRecentTab'] = static::MAX_PROJECTS_IN_RECENT_TAB;
138 if (isset(
$options[
'maxProjectsInRecentTab']) && is_int(
$options[
'maxProjectsInRecentTab']))
140 $this->options[
'maxProjectsInRecentTab'] = max(
142 min(
$options[
'maxProjectsInRecentTab'], static::MAX_PROJECTS_IN_RECENT_TAB)
146 $this->options[
'searchLimit'] = static::SEARCH_LIMIT;
149 $this->options[
'searchLimit'] = max(1, min(
$options[
'searchLimit'], static::SEARCH_LIMIT));
152 $this->options[
'shouldSelectProjectDates'] =
false;
153 if (isset(
$options[
'shouldSelectProjectDates']) && is_bool(
$options[
'shouldSelectProjectDates']))
155 $this->options[
'shouldSelectProjectDates'] = (bool)
$options[
'shouldSelectProjectDates'];
158 $this->options[
'shouldSelectDialogId'] =
false;
159 if (isset(
$options[
'shouldSelectDialogId']) && is_bool(
$options[
'shouldSelectDialogId']))
161 $this->options[
'shouldSelectDialogId'] =
$options[
'shouldSelectDialogId'];
164 $this->options[
'checkCollabInviteOption'] =
false;
165 if (isset(
$options[
'checkCollabInviteOption']) && is_bool(
$options[
'checkCollabInviteOption']))
167 $this->options[
'checkCollabInviteOption'] =
$options[
'checkCollabInviteOption'];
174 $this->options[
'addProjectMetaUsers'] =
false;
175 if (isset(
$options[
'addProjectMetaUsers']) && is_bool(
$options[
'addProjectMetaUsers']))
177 $this->options[
'addProjectMetaUsers'] = (bool)
$options[
'addProjectMetaUsers'];
183 return $GLOBALS[
'USER']->isAuthorized();
204 'myProjectsOnly' =>
false,
212 $dialog->addItems($this->
makeProjectItems($projects, [
'tabs' =>
'projects']));
215 $isCollaber =
$user->isCollaber();
228 $dialog->addTab(
new Tab([
230 'title' => Loc::getMessage(
'SOCNET_ENTITY_SELECTOR_COLLAB_TAB_TITLE'),
233 'default' =>
'/bitrix/js/socialnetwork/entity-selector/src/images/collab-tab-icon.svg',
234 'selected' =>
'/bitrix/js/socialnetwork/entity-selector/src/images/collab-tab-icon-selected.svg'
241 'data:image/svg+xml;charset=US-ASCII,%3Csvg%20width%3D%2223%22%20height%3D%2223%22%20'.
242 'fill%3D%22none%22%20xmlns%3D%22http%3A//www.w3.org/2000/svg%22%3E%3Cpath%20d%3D%22M11'.
243 '.934%202.213a.719.719%200%2001.719%200l3.103%201.79c.222.13.36.367.36.623V8.21a.719.71'.
244 '9%200%2001-.36.623l-3.103%201.791a.72.72%200%2001-.719%200L8.831%208.832a.719.719%200%'.
245 '2001-.36-.623V4.627c0-.257.138-.495.36-.623l3.103-1.791zM7.038%2010.605a.719.719%200%2'.
246 '001.719%200l3.103%201.792a.72.72%200%2001.359.622v3.583a.72.72%200%2001-.36.622l-3.102'.
247 '%201.792a.719.719%200%2001-.72%200l-3.102-1.791a.72.72%200%2001-.36-.623v-3.583c0-.257'.
248 '.138-.494.36-.622l3.103-1.792zM20.829%2013.02a.719.719%200%2000-.36-.623l-3.102-1.792a'.
249 '.719.719%200%2000-.72%200l-3.102%201.792a.72.72%200%2000-.36.622v3.583a.72.72%200%2000'.
250 '.36.622l3.103%201.792a.719.719%200%2000.719%200l3.102-1.791a.719.719%200%2000.36-.623v'.
251 '-3.583z%22%20fill%3D%22%23ABB1B8%22/%3E%3C/svg%3E';
253 $dialog->addTab(
new Tab([
255 'title' => Loc::getMessage(
'SOCNET_ENTITY_SELECTOR_PROJECTS_TAB_TITLE'),
259 'selected' => str_replace(
'ABB1B8',
'fff', $icon),
266 $onlyProjectsMode =
count($dialog->getEntities()) === 1;
269 $this->options[
'fillRecentTab'] ===
true ||
270 ($this->options[
'fillRecentTab'] !==
false && $onlyProjectsMode)
275 $this->fillRecentTab($dialog, $projects);
279 $this->options[
'createProjectLink'] ===
true ||
280 ($this->options[
'createProjectLink'] !==
false && $onlyProjectsMode)
284 $this->options[
'checkFeatureForCreate']
285 && !Feature::isFeatureEnabled(Feature::PROJECTS_GROUPS)
288 $createProjectLink =
false;
291 if ($createProjectLink && self::canCreateProject())
294 if ($dialog->getFooter() ===
'BX.SocialNetwork.EntitySelector.Footer')
297 $footerOptions = $dialog->getFooterOptions() ?? [];
300 if ($this->options[
'lockProjectLink'])
302 $footerOptions[
'lockProjectLink'] =
true;
303 $footerOptions[
'lockProjectLinkFeatureId'] = $this->options[
'lockProjectLinkFeatureId'] ??
'';
307 $dialog->setFooter(
'BX.SocialNetwork.EntitySelector.Footer', $footerOptions);
322 return static::getProjects(
$options);
337 $isProjectsEnabled =
true;
338 $isScrumEnabled =
true;
339 if (Loader::includeModule(
'intranet'))
341 $toolsManager = ToolsManager::getInstance();
342 $isProjectsEnabled = $toolsManager->checkAvailabilityByToolId(
'projects');
343 $isScrumEnabled = $toolsManager->checkAvailabilityByToolId(
'scrum');
344 if (!$isProjectsEnabled && !$isScrumEnabled)
350 $query = WorkgroupTable::query();
367 isset(
$options[
'shouldSelectProjectDates'])
368 && is_bool(isset(
$options[
'shouldSelectProjectDates']))
369 &&
$options[
'shouldSelectProjectDates']
407 if (!CollabFeature::isFeatureEnabledInPortalSettings())
411 if (is_array(
$options[
'!type']) && !in_array(Type::Collab->value,
$options[
'!type']))
413 $options[
'!type'][] = Type::Collab->value;
421 ->whereNotIn(
'TYPE',
$options[
'!type'])
436 Filter\Helper::matchAgainstWildcard(
437 Content::prepareStringToken(
$options[
'searchQuery']),
444 $currentUserId = (!empty(
$options[
'currentUserId']) && is_int(
$options[
'currentUserId'])
447 $query->registerRuntimeField(
450 WorkgroupSiteTable::class,
451 Join::on(
'this.ID',
'ref.GROUP_ID'),
452 [
'join_type' =>
'INNER']
459 $options[
'myProjectsOnly'] ??=
true;
460 $notOnlyMyProjects = (
$options[
'myProjectsOnly'] ===
false);
462 $currentUserModuleAdmin = \CSocNetUser::isCurrentUserModuleAdmin();
463 if (!$currentUserModuleAdmin)
465 $query->registerRuntimeField(
468 UserToGroupTable::class,
469 Join::on(
'this.ID',
'ref.GROUP_ID')
470 ->where(
'ref.USER_ID', $currentUserId)
476 [
'join_type' => $notOnlyMyProjects ? Join::TYPE_LEFT : Join::TYPE_INNER]
479 $query->addSelect(
'MY_PROJECT.ROLE',
'PROJECT_ROLE');
484 $query->registerRuntimeField(
487 WorkgroupViewTable::class,
488 Join::on(
'this.ID',
'ref.GROUP_ID')->where(
'ref.USER_ID', $currentUserId),
489 [
'join_type' =>
'INNER']
494 if (
$options[
'checkCollabInviteOption'] ??
false)
496 if ($currentUserModuleAdmin)
499 $query->registerRuntimeField(
502 UserToGroupTable::class,
503 Join::on(
'this.ID',
'ref.GROUP_ID')
504 ->where(
'ref.USER_ID', $currentUserId),
505 [
'join_type' => Join::TYPE_INNER]
510 $query->registerRuntimeField(
513 CollabOptionTable::class,
514 Join::on(
'this.ID',
'ref.COLLAB_ID')
515 ->where(
'ref.NAME', WhoCanInviteOption::DB_NAME),
516 [
'join_type' => Join::TYPE_INNER]
526 WHEN %s = '{$ownerRole}' THEN 2
527 WHEN %s = '{$managerRole}' THEN 1
530 [
'COLLAB_OPTIONS.VALUE',
'COLLAB_OPTIONS.VALUE']
531 ))->configureValueType(IntegerField::class));
536 WHEN %s = '{$ownerRole}' THEN 2
537 WHEN %s = '{$managerRole}' THEN 1
538 WHEN %s = '{$userRole}' THEN 0
541 [
'MY_PROJECT.ROLE',
'MY_PROJECT.ROLE',
'MY_PROJECT.ROLE']
542 ))->configureValueType(IntegerField::class));
545 'HAS_ACCESS_BY_ROLE',
547 [
'ROLE_WEIGHT',
'NEED_ROLE_WEIGHT']
548 ))->configureValueType(BooleanField::class),
'expr',
true);
551 $extranetSiteId = Option::get(
'extranet',
'extranet_site');
554 && ModuleManager::isModuleInstalled(
'extranet') ? $extranetSiteId :
false
558 $query->registerRuntimeField(
561 WorkgroupSiteTable::class,
562 Join::on(
'this.ID',
'ref.GROUP_ID')->where(
'ref.SITE_ID', $extranetSiteId),
563 [
'join_type' =>
'LEFT']
567 $query->registerRuntimeField(
569 'IS_EXTRANET',
'CASE WHEN %s IS NOT NULL THEN \'Y\' ELSE \'N\' END', [
'EXTRANET_PROJECT.GROUP_ID']
573 $query->addSelect(
'IS_EXTRANET');
579 $query->whereNotNull(
'EXTRANET_PROJECT.GROUP_ID');
583 $query->whereNull(
'EXTRANET_PROJECT.GROUP_ID');
592 : (isset(
$options[
'!projectId']) ?
'!projectId' :
null)
595 if (isset(
$options[$projectFilter]))
599 foreach (
$options[$projectFilter] as $id)
601 $projectIds[] = (int)$id;
604 $projectIds = array_unique($projectIds);
606 if (!empty($projectIds))
608 if ($projectFilter ===
'projectId')
610 $query->whereIn(
'ID', $projectIds);
614 $query->whereNotIn(
'ID', $projectIds);
618 else if (!is_array(
$options[$projectFilter]) && (
int)
$options[$projectFilter] > 0)
620 if ($projectFilter ===
'projectId')
632 $projectFilter ===
'projectId'
634 && ($projectsCount =
count($projectIds)) > 1
637 $helper = Application::getConnection()->getSqlHelper();
640 $helper->getOrderByIntField(
'%s', $projectIds,
false),
641 array_fill(0, $projectsCount,
'ID')
645 ->registerRuntimeField($field)
646 ->setOrder($field->getName());
654 $query->setOrder([
'NAME' =>
'asc']);
657 $isUserModuleAdmin = \CSocNetUser::isUserModuleAdmin($currentUserId,
$siteId);
665 foreach (array_keys(
$options[
'features']) as $feature)
667 if (!self::isAllowedFeatures($feature))
675 Join::on(
'this.ID',
'ref.ENTITY_ID')
677 ->where(
'ref.FEATURE', $feature)
678 ->where(
'ref.ACTIVE',
'N'),
679 [
'join_type' =>
'LEFT']
681 $query->registerRuntimeField($featureField);
683 $query->whereNull(
"BF_{$feature}.ENTITY_ID");
686 if (!$isUserModuleAdmin)
692 if ($featuresPermissionsQuery)
694 $query->whereIn(
'ID', $featuresPermissionsQuery);
699 if (!$isProjectsEnabled)
701 $query->whereNotNull(
'SCRUM_MASTER_ID');
704 if (!$isScrumEnabled)
706 $query->whereNull(
'SCRUM_MASTER_ID');
713 elseif ($projectFilter !==
'projectId' || empty($projectIds))
718 $eoWorkgroups =
$query->exec()->fetchCollection();
720 if ($currentUserModuleAdmin)
722 return $eoWorkgroups;
726 foreach ($eoWorkgroups as $eoWorkgroup)
728 $isMember =
$query->getEntity()->hasField(
'MY_PROJECT') && !empty($eoWorkgroup->get(
'MY_PROJECT'));
729 $notSecretGroup = $eoWorkgroup->getVisible() ===
true;
730 if ($isMember || ($notOnlyMyProjects && $notSecretGroup))
732 $workgroups->add($eoWorkgroup);
736 if (
$options[
'shouldSelectDialogId'] ??
false)
738 $chatData = Workgroup::getChatData([
739 'group_id' => array_diff($workgroups->getIdList(), array_keys(static::$groupDialogIds)),
740 'skipAvailabilityCheck' =>
true,
743 foreach ($workgroups as $workgroup)
745 $id = $workgroup->getId();
753 private static function isAllowedFeatures($feature =
''): bool
755 static $globalFeatures =
null;
757 if ($globalFeatures ===
null)
759 $globalFeatures = \CSocNetAllowed::getAllowedFeatures();
763 !isset($globalFeatures[$feature][
'allowed'])
764 || !is_array($globalFeatures[$feature][
'allowed'])
766 || mb_strlen($feature) <= 0
780 if (!self::isAllowedFeatures($feature))
785 $subQuery = FeatureTable::query();
787 $subQuery->where(
'FEATURE', $feature);
788 $subQuery->where(
'ACTIVE',
'N');
789 $subQuery->registerRuntimeField(
791 'IS_INACTIVE_IN_GROUP',
"CASE WHEN {$alias}.ID = %s THEN 1 ELSE 0 END",
'ENTITY_ID'
794 $subQuery->where(
'IS_INACTIVE_IN_GROUP', 1);
805 $globalFeatures = \CSocNetAllowed::getAllowedFeatures();
807 $workWithClosedGroups = (Option::get(
'socialnetwork',
'work_with_closed_groups',
'N') ===
'Y');
809 $query = new \Bitrix\Main\Entity\Query(WorkgroupTable::getEntity());
812 if ($currentUserId > 0)
816 UserToGroupTable::getEntity(),
817 Join::on(
'this.ID',
'ref.GROUP_ID')
818 ->where(
'ref.USER_ID', $currentUserId),
819 [
'join_type' =>
'INNER' ]
825 $featureEntity = clone FeatureTable::getEntity();
827 foreach ($featuresList as $feature => $operationsList)
829 if (empty($operationsList))
837 foreach ($globalFeatures[$feature][
'operations'] as $operation => $perms)
840 !in_array($operation, $operationsList,
true)
856 Join::on(
'this.ID',
'ref.ENTITY_ID')
858 ->where(
'ref.FEATURE', $feature),
859 [
'join_type' =>
'LEFT' ]
864 FeaturePermTable::class,
865 Join::on(
'this.ID',
'ref.FEATURE_ID'),
866 [
'join_type' =>
'LEFT' ]
871 ->whereIn(
"F_{$feature}.FP_{$feature}.OPERATION_ID", $operationsList)
872 ->whereNull(
"F_{$feature}.FP_{$feature}.OPERATION_ID")
875 if ($currentUserId > 0)
877 $minOperationsList = ($globalFeatures[$feature][
'minoperation'] ?? []);
878 if (!is_array($minOperationsList))
880 $minOperationsList = [ $minOperationsList ];
883 $conditionsList = [];
886 if (!$workWithClosedGroups && !empty($minOperationsList))
888 $minOperations = implode(
', ', array_map(
static function($operation) use ($helper) {
return "'" . $helper->forSql($operation) .
"'"; }, $minOperationsList));
889 $conditionsList[] =
"WHEN %s = 'Y' AND %s NOT IN ({$minOperations}) THEN 'A'";
890 $substitutes[] =
'CLOSED';
891 $substitutes[] =
"F_{$feature}.FP_{$feature}.OPERATION_ID";
894 $conditionsList[] =
"WHEN %s = 'N' AND %s IN ('N', 'L') THEN 'K'";
895 $substitutes[] =
'VISIBLE';
896 $substitutes[] =
"F_{$feature}.FP_{$feature}.ROLE";
898 $conditionsList[] =
'WHEN %s IS NOT NULL THEN %s';
899 $substitutes[] =
"F_{$feature}.FP_{$feature}.ROLE";
900 $substitutes[] =
"F_{$feature}.FP_{$feature}.ROLE";
902 $conditions = implode(
' ', $conditionsList);
905 "MIN_PERMISSION_{$feature}",
906 "CASE {$conditions} ELSE '{$defaultPerm}' END",
910 $query->registerRuntimeField(
912 "HAS_ACCESS_{$feature}",
913 'CASE WHEN %s <= %s THEN 1 ELSE 0 END',
916 "MIN_PERMISSION_{$feature}",
920 $query->where(
"HAS_ACCESS_{$feature}", 1);
925 "MIN_PERMISSION_{$feature}",
926 "CASE WHEN %s IS NOT NULL THEN %s ELSE '{$defaultPerm}' END",
928 "F_{$feature}.FP_{$feature}.ROLE",
929 "F_{$feature}.FP_{$feature}.ROLE"
933 $query->where(
"MIN_PERMISSION_{$feature}",
'N');
937 return ($hasFilter ?
$query :
false);
944 if (empty($features))
949 $projectIds = $projects->getIdList();
950 foreach ($features as $feature => $operations)
952 $availableIds = \CSocNetFeatures::isActiveFeature(
SONET_ENTITY_GROUP, $projectIds, $feature);
953 if (!is_array($availableIds))
958 $hasUnavailableId =
false;
963 $hasUnavailableId =
true;
964 $projects->removeByPrimary($projectId);
968 if ($hasUnavailableId)
970 $projectIds = $projects->getIdList();
974 $isUserModuleAdmin = \CSocNetUser::isUserModuleAdmin(
$userId,
$siteId);
975 $availableIdsByFeature = [];
978 foreach ($features as $feature => $operations)
980 if (!is_array($operations) || empty($operations))
982 $availableIdsByFeature[] = $projectIds;
986 $availableFeatureIds = [];
988 foreach ($operations as $operation)
995 $availableIds = \CSocNetFeaturesPerms::canPerformOperation(
1004 if (!is_array($availableIds))
1013 $availableFeatureIds[] = $projectId;
1017 $ids = array_diff($ids, $availableFeatureIds);
1020 $availableIdsByFeature[] = $availableFeatureIds;
1024 if (!empty($availableIdsByFeature))
1027 count($availableIdsByFeature) > 1
1028 ? call_user_func_array(
'array_intersect', $availableIdsByFeature)
1029 : $availableIdsByFeature[0]
1033 if (empty($availableIds))
1038 $wrongIds = array_diff($projects->getIdList(), $availableIds);
1039 foreach ($wrongIds as $wrongId)
1041 $projects->removeByPrimary($wrongId);
1050 foreach ($projects as $project)
1066 $extranetSiteId = Option::get(
'extranet',
'extranet_site');
1067 $extranetSiteId = ($extranetSiteId && ModuleManager::isModuleInstalled(
'extranet') ? $extranetSiteId :
false);
1068 $isExtranet = ($extranetSiteId && $project->get(
'IS_EXTRANET') ===
'Y');
1069 $isCollab = $project->getType() === Type::Collab->value;
1072 'id' => $project->getId(),
1073 'entityId' => static::ENTITY_ID,
1074 'entityType' => self::makeProjectEntityType($project),
1075 'title' => $project->getName(),
1076 'avatar' => self::makeProjectAvatar($project),
1078 'landing' => $project->getLanding(),
1079 'active' => $project->getActive(),
1080 'visible' => $project->getVisible(),
1081 'closed' => $project->getClosed(),
1082 'open' => $project->getOpened(),
1083 'project' => $project->getProject(),
1084 'isCollab' => $isCollab,
1085 'isExtranet' => $isExtranet,
1087 'dateStart' => $project->getProjectDateStart()?->getTimestamp(),
1088 'dateFinish' => $project->getProjectDateFinish()?->getTimestamp(),
1093 if (
$options[
'shouldSelectDialogId'] ??
false)
1095 $item->getCustomData()->set(
'dialogId', static::$groupDialogIds[$project->getId()]);
1103 if (isset(
$options[
'addProjectMetaUsers']) &&
$options[
'addProjectMetaUsers'] ===
true)
1105 $item->addChild(
new Item([
1106 'id' => $project->getId() .
':A',
1107 'title' => $project->getName() .
'. ' . Loc::getMessage(
'SOCNET_ENTITY_SELECTOR_PROJECTS_METAUSER_OWNER'),
1108 'entityId' => static::ENTITY_ID,
1109 'entityType' =>
'project_metauser',
1111 'title' => Loc::getMessage(
'SOCNET_ENTITY_SELECTOR_PROJECTS_METAUSER_OWNER'),
1112 'renderMode' =>
'override',
1115 'projectId' => $project->getId(),
1116 'metauser' =>
'owner'
1120 $item->addChild(
new Item([
1121 'id' => $project->getId() .
':E',
1122 'title' => $project->getName() .
'. ' . Loc::getMessage(
'SOCNET_ENTITY_SELECTOR_PROJECTS_METAUSER_MODERATOR'),
1123 'entityType' =>
'project_metauser',
1124 'entityId' => static::ENTITY_ID,
1126 'title' => Loc::getMessage(
'SOCNET_ENTITY_SELECTOR_PROJECTS_METAUSER_MODERATOR'),
1127 'renderMode' =>
'override',
1130 'projectId' => $project->getId(),
1131 'metauser' =>
'moderator'
1135 $item->addChild(
new Item([
1136 'id' => $project->getId() .
':K',
1137 'title' => $project->getName() .
'. ' . Loc::getMessage(
'SOCNET_ENTITY_SELECTOR_PROJECTS_METAUSER_ALL'),
1138 'entityId' => static::ENTITY_ID,
1139 'entityType' =>
'project_metauser',
1141 'title' => Loc::getMessage(
'SOCNET_ENTITY_SELECTOR_PROJECTS_METAUSER_ALL'),
1142 'renderMode' =>
'override',
1145 'projectId' => $project->getId(),
1156 if (!empty($project->getImageId()))
1158 $avatar = \CFile::resizeImageGet(
1159 $project->getImageId(),
1160 [
'width' => 100,
'height' => 100],
1165 return !empty($avatar[
'src']) ? $avatar[
'src'] :
null;
1168 if (!empty($project->getAvatarType()))
1170 $url = \Bitrix\Socialnetwork\Helper\Workgroup::getAvatarEntitySelectorUrl($project->getAvatarType());
1179 $extranetSiteId = Option::get(
'extranet',
'extranet_site');
1180 $extranetSiteId = ($extranetSiteId && ModuleManager::isModuleInstalled(
'extranet') ? $extranetSiteId :
false);
1181 $isExtranet = ($extranetSiteId && $project->get(
'IS_EXTRANET') ===
'Y');
1182 $isCollab = $project->getType() === Type::Collab->value;
1184 return ($isExtranet && !$isCollab) ?
'extranet' : $project->getType();
1187 public static function getProjectUrl(?
int $projectId =
null, ?
int $currentUserId =
null): string
1191 $extranetSiteId = Option::get(
'extranet',
'extranet_site');
1192 $projectPage = Option::get(
'socialnetwork',
'workgroups_page',
false, $extranetSiteId);
1195 $projectPage =
'/extranet/workgroups/';
1200 $projectPage = Option::get(
'socialnetwork',
'workgroups_page',
false,
SITE_ID);
1203 $projectPage =
SITE_DIR.
'workgroups/';
1207 return $projectPage.
'group/'.($projectId !==
null ? $projectId :
'#id#').
'/';
1218 return $userPage .
'groups/create/';
1223 return \Bitrix\Socialnetwork\Helper\Workgroup\Access::canCreate();
1228 $recentItems = $dialog->getRecentItems()->getEntityItems(static::ENTITY_ID);
1230 if (
count($recentItems) < $this->options[
'maxProjectsInRecentTab'])
1232 $limit = $this->options[
'maxProjectsInRecentTab'] -
count($recentItems);
1233 $recentGlobalItems = $dialog->getGlobalRecentItems()->getEntityItems(static::ENTITY_ID);
1234 foreach ($recentGlobalItems as $recentGlobalItem)
1241 if (!isset($recentItems[$recentGlobalItem->getId()]) && $recentGlobalItem->isLoaded())
1243 $dialog->getRecentItems()->add($recentGlobalItem);
1248 $recentItems = $dialog->getRecentItems()->getEntityItems(static::ENTITY_ID);
1251 if (
count($recentItems) < $this->options[
'maxProjectsInRecentTab'])
1253 $recentIds = array_map(
'intval', array_keys($recentItems));
1255 $dialog->addRecentItems(
1257 '!projectId' => $recentIds,
1259 'order' => [
'VIEWED_PROJECT.DATE_VIEW' =>
'desc'],
1260 'limit' => $this->options[
'maxProjectsInRecentTab'] -
count($recentItems)
1264 $recentItems = $dialog->getRecentItems()->getEntityItems(static::ENTITY_ID);
1267 if (
count($recentItems) < $this->options[
'maxProjectsInRecentTab'])
1269 $limit = $this->options[
'maxProjectsInRecentTab'] -
count($recentItems);
1270 foreach ($projects as $project)
1277 if (isset($recentItems[$project->getId()]))
1282 $dialog->getRecentItems()->add(
1284 'id' => $project->getId(),
1285 'entityId' => static::ENTITY_ID,
if(!is_object($USER)||! $USER->IsAuthorized()) $userId
static getDialogId(int $chatId, $userId=null)
static getConnection($name="")
const FEATURE_ENTITY_TYPE_GROUP
static getProjects(array $options=[])
static makeItem(EO_Workgroup $project, $options=[])
static makeProjectAvatar(EO_Workgroup $project)
static getProjectUrl(?int $projectId=null, ?int $currentUserId=null)
__construct(array $options=[])
static canCreateProject()
static makeItems(EO_Workgroup_Collection $projects, $options=[])
static getFeaturesPermissionsQuery($currentUserId, $featuresList=[])
static makeProjectEntityType(EO_Workgroup $project)
fillDialog(Dialog $dialog)
getPreselectedItems(array $ids)
getProjectItems(array $options=[])
getProjectCollection(array $options=[])
static getCreateProjectUrl(?int $currentUserId=null)
makeProjectItems(EO_Workgroup_Collection $projects, array $options=[])
static filterByFeatures(EO_Workgroup_Collection $projects, array $features, int $userId, string $siteId)
const MAX_PROJECTS_IN_RECENT_TAB
getSelectedItems(array $ids)
doSearch(SearchQuery $searchQuery, Dialog $dialog)
static getFeatureQuery($alias, $feature='')
static isExtranetUser(int $userId=null)
static getCurrentUserId()
static getIntranetUserUrl(?int $userId=null)
static getExtranetUserUrl(?int $userId=null)
</td ></tr ></table ></td ></tr >< tr >< td class="bx-popup-label bx-width30"><?=GetMessage("PAGE_NEW_TAGS")?> array( $site)
const BX_RESIZE_IMAGE_EXACT
const SITE_DIR(!defined('LANG'))
$GLOBALS['____1690880296']
if( $daysToExpire >=0 &&$daysToExpire< 60 elseif)( $daysToExpire< 0)
</p ></td >< td valign=top style='border-top:none;border-left:none;border-bottom:solid windowtext 1.0pt;border-right:solid windowtext 1.0pt;padding:0cm 2.0pt 0cm 2.0pt;height:9.0pt'>< p class=Normal align=center style='margin:0cm;margin-bottom:.0001pt;text-align:center;line-height:normal'>< a name=ТекстовоеПоле54 ></a ><?=($taxRate > count( $arTaxList) > 0) ? $taxRate."%"