diff --git a/application/Espo/Core/SelectManagers/Base.php b/application/Espo/Core/SelectManagers/Base.php index c82aa52de6..8259cfcc6f 100644 --- a/application/Espo/Core/SelectManagers/Base.php +++ b/application/Espo/Core/SelectManagers/Base.php @@ -52,6 +52,8 @@ class Base private $userTimeZone = null; + protected $additionalFilterTypeList = ['linkedWith', 'inCategory', 'isUserFromTeams']; + const MIN_LENGTH_FOR_CONTENT_SEARCH = 4; public function __construct($entityManager, \Espo\Entities\User $user, Acl $acl, $metadata) @@ -158,77 +160,108 @@ class Base } } - $linkedWith = array(); - $inCategory = array(); - $ignoreList = ['linkedWith', 'inCategory', 'bool', 'primary']; + $ignoreTypeList = array_merge(['bool', 'primary'], $this->additionalFilterTypeList); + + $additionalFilters = array(); foreach ($where as $item) { - if (!in_array($item['type'], $ignoreList)) { + $type = $item['type']; + if (!in_array($type, $ignoreTypeList)) { $part = $this->getWherePart($item); if (!empty($part)) { $whereClause[] = $part; } } else { - if ($item['type'] == 'linkedWith' && !empty($item['value'])) { - $linkedWith[$item['field']] = $item['value']; - } else if ($item['type'] == 'inCategory' && !empty($item['value'])) { - $inCategory[$item['field']] = $item['value']; + if (in_array($type, $this->additionalFilterTypeList)) { + if (!empty($item['value'])) { + $methodName = 'apply' . ucfirst($type); + + if (method_exists($this, $methodName)) {; + $this->$methodName($item['field'], $item['value'], $result); + } + } } } } $result['whereClause'] = array_merge($result['whereClause'], $whereClause); - - if (!empty($linkedWith)) { - $this->handleLinkedWith($linkedWith, $result); - } - if (!empty($inCategory)) { - $this->handleInCategory($inCategory, $result); - } } - protected function handleLinkedWith($linkedWith, &$result) + protected function applyLinkedWith($link, $idsValue, &$result) { - $joins = []; - $part = array(); - foreach ($linkedWith as $link => $idsValue) { - if (is_array($idsValue) && count($idsValue) == 1) { - $idsValue = $idsValue[0]; - } - $relDefs = $this->getSeed()->getRelations(); + if (is_array($idsValue) && count($idsValue) == 1) { + $idsValue = $idsValue[0]; + } - if (!empty($relDefs[$link])) { - $defs = $relDefs[$link]; - if ($defs['type'] == 'manyMany') { - $joins[] = $link; - if (!empty($defs['midKeys'])) { - $key = $defs['midKeys'][1]; - $part[$link . 'Middle.' . $key] = $idsValue; - } - } else if ($defs['type'] == 'belongsTo') { - if (!empty($defs['key'])) { - $key = $defs['key']; - $part[$key] = $idsValue; - } - } + $seed = $this->getSeed(); + + if (!$seed->hasRelation($link)) return; + + $relDefs = $this->getSeed()->getRelations(); + + $relationType = $seed->getRelationType($link); + + $defs = $relDefs[$link]; + if ($relationType == 'manyMany') { + $this->addJoin($link, $result); + $midKeys = $seed->getRelationParam($link, 'midKeys'); + + if (!empty($midKeys)) { + $key = $midKeys[1]; + $part[$link . 'Middle.' . $key] = $idsValue; } + } else if ($relationType== 'belongsTo') { + $key = $seed->getRelationParam($link, 'key'); + if (!empty($key)) { + $part[$key] = $idsValue; + } + } else { + return; } if (!empty($part)) { $result['whereClause'][] = $part; } - $result['joins'] = array_merge($result['joins'], $joins); - $result['joins'] = array_unique($result['joins']); - $result['distinct'] = true; + + $this->setDistinct(true, $result); } - protected function handleInCategory($inCategory, &$result) + protected function applyIsUserFromTeams($link, $idsValue, &$result) { - foreach ($inCategory as $link => $value) { - $this->applyInCategory($link, $value, $result); + if (is_array($idsValue) && count($idsValue) == 1) { + $idsValue = $idsValue[0]; } + + $query = $this->getEntityManager()->getQuery(); + + $seed = $this->getSeed(); + + $relDefs = $seed->getRelations(); + + if (!$seed->hasRelation($link)) return; + + $relationType = $seed->getRelationType($link); + + if ($relationType == 'belongsTo') { + $key = $seed->getRelationParam($link, 'key'); + + $aliasName = 'usersTeams' . ucfirst($link); + + $result['customJoin'] .= " + JOIN team_user AS {$aliasName}Middle ON {$aliasName}Middle.user_id = ".$query->toDb($seed->getEntityType()).".".$query->toDb($key)." AND {$aliasName}Middle.deleted = 0 + JOIN team AS {$aliasName} ON {$aliasName}.deleted = 0 AND {$aliasName}Middle.team_id = {$aliasName}.id + "; + + $result['whereClause'][] = array( + $aliasName . 'Middle.teamId' => $idsValue + ); + } else { + return; + } + + $this->setDistinct(true, $result); } public function applyInCategory($link, $value, &$result) diff --git a/application/Espo/Core/Templates/Metadata/Base/entityDefs.json b/application/Espo/Core/Templates/Metadata/Base/entityDefs.json index 9a9a450619..db59ce8f03 100644 --- a/application/Espo/Core/Templates/Metadata/Base/entityDefs.json +++ b/application/Espo/Core/Templates/Metadata/Base/entityDefs.json @@ -17,15 +17,18 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { "type": "link", - "required": true + "required": true, + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Core/Templates/Metadata/CategoryTree/entityDefs.json b/application/Espo/Core/Templates/Metadata/CategoryTree/entityDefs.json index 09a1e59d18..d8b23660b4 100644 --- a/application/Espo/Core/Templates/Metadata/CategoryTree/entityDefs.json +++ b/application/Espo/Core/Templates/Metadata/CategoryTree/entityDefs.json @@ -22,11 +22,13 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Core/Templates/Metadata/Person/entityDefs.json b/application/Espo/Core/Templates/Metadata/Person/entityDefs.json index 5d5ab4b3f6..54f9ba53b9 100644 --- a/application/Espo/Core/Templates/Metadata/Person/entityDefs.json +++ b/application/Espo/Core/Templates/Metadata/Person/entityDefs.json @@ -59,15 +59,18 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { "type": "link", - "required": true + "required": false, + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Account.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Account.json index 8bb0046009..350e30107d 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Account.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Account.json @@ -126,14 +126,17 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { - "type": "link" + "type": "link", + "view": "views/fields/assigned-user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Call.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Call.json index e74fb5062f..3e8686addd 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Call.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Call.json @@ -97,15 +97,18 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { "type": "link", - "required": true + "required": true, + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Campaign.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Campaign.json index dd83e7bc95..1ca7a62e94 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Campaign.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Campaign.json @@ -34,14 +34,17 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { - "type": "link" + "type": "link", + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Case.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Case.json index 10b562a503..20edf111c4 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Case.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Case.json @@ -60,14 +60,17 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { - "type": "link" + "type": "link", + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Contact.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Contact.json index 7107f0d7d0..5f21ac9328 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Contact.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Contact.json @@ -116,14 +116,17 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { - "type": "link" + "type": "link", + "view": "views/fields/assigned-user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Document.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Document.json index 38123879aa..dce29e4509 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Document.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Document.json @@ -50,14 +50,17 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { - "type": "link" + "type": "link", + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Lead.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Lead.json index b735d875e4..d23365f7f9 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Lead.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Lead.json @@ -94,17 +94,20 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "accountName": { "type": "varchar" }, "assignedUser": { - "type": "link" + "type": "link", + "view": "views/fields/user" }, "acceptanceStatus": { "type": "varchar", diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Meeting.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Meeting.json index 585467c97c..c20eecfedd 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Meeting.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Meeting.json @@ -92,15 +92,18 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { "type": "link", - "required": true + "required": true, + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Opportunity.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Opportunity.json index fe6e5b880b..86d24a58d1 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Opportunity.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Opportunity.json @@ -80,15 +80,18 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { "type": "link", - "required": false + "required": false, + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Target.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Target.json index 81cb7b0046..ac4a3c6da6 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Target.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Target.json @@ -73,15 +73,17 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { "type": "link", - "required": true + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/TargetList.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/TargetList.json index 21188b71b9..5d3d31bd2a 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/TargetList.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/TargetList.json @@ -22,14 +22,17 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { - "type": "link" + "type": "link", + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Task.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Task.json index 5a05548f22..c5dccff71a 100644 --- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Task.json +++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Task.json @@ -71,15 +71,18 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { "type": "link", - "required": true + "required": true, + "view": "views/fields/user" }, "teams": { "type": "linkMultiple" diff --git a/application/Espo/Resources/i18n/en_US/Global.json b/application/Espo/Resources/i18n/en_US/Global.json index 3e9a15966d..f157c1f790 100644 --- a/application/Espo/Resources/i18n/en_US/Global.json +++ b/application/Espo/Resources/i18n/en_US/Global.json @@ -447,7 +447,8 @@ "is": "Is", "isEmpty": "Is Empty", "isNotEmpty": "Is Not Empty", - "isOneOf": "Is One Of" + "isOneOf": "Is One Of", + "isFromTeams": "Is From Team" }, "varcharSearchRanges": { "equals": "Equals", diff --git a/application/Espo/Resources/metadata/entityDefs/Email.json b/application/Espo/Resources/metadata/entityDefs/Email.json index ab36a37e7b..19866dcf8c 100644 --- a/application/Espo/Resources/metadata/entityDefs/Email.json +++ b/application/Espo/Resources/metadata/entityDefs/Email.json @@ -171,15 +171,18 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "assignedUser": { "type": "link", - "required": false + "required": false, + "view": "views/fields/user" }, "replied": { "type": "link", diff --git a/application/Espo/Resources/metadata/entityDefs/EmailTemplate.json b/application/Espo/Resources/metadata/entityDefs/EmailTemplate.json index 4411d20862..cff2c13ad8 100644 --- a/application/Espo/Resources/metadata/entityDefs/EmailTemplate.json +++ b/application/Espo/Resources/metadata/entityDefs/EmailTemplate.json @@ -37,11 +37,13 @@ }, "modifiedAt": { "type": "datetime", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "modifiedBy": { "type": "link", diff --git a/application/Espo/Resources/metadata/entityDefs/Portal.json b/application/Espo/Resources/metadata/entityDefs/Portal.json index 101ba1af6c..7f890f15b3 100644 --- a/application/Espo/Resources/metadata/entityDefs/Portal.json +++ b/application/Espo/Resources/metadata/entityDefs/Portal.json @@ -91,7 +91,8 @@ }, "modifiedBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" }, "createdAt": { "type": "datetime", @@ -99,7 +100,8 @@ }, "createdBy": { "type": "link", - "readOnly": true + "readOnly": true, + "view": "views/fields/user" } }, "links": { diff --git a/frontend/client/res/templates/fields/link/search.tpl b/frontend/client/res/templates/fields/link/search.tpl index b6adee9a87..236dc3d35b 100644 --- a/frontend/client/res/templates/fields/link/search.tpl +++ b/frontend/client/res/templates/fields/link/search.tpl @@ -13,7 +13,7 @@