Compare commits

..

11 Commits
5.4.0 ... 5.4.2

Author SHA1 Message Date
yuri
e743f61913 version 2018-09-10 12:17:15 +03:00
yuri
7f4e5dd01a note acl populate script 2018-09-10 12:15:42 +03:00
yuri
8a1b58cf7c fix kanban css 2018-09-10 11:22:22 +03:00
yuri
2a20766912 fix UniquId 2018-09-10 10:29:34 +03:00
yuri
b49679eb90 fix notification id 2018-09-10 10:27:09 +03:00
yuri
b2ea073c16 fix notifications 2018-09-10 10:24:09 +03:00
yuri
54085a59c3 fix meeting acl 2018-09-07 14:38:02 +03:00
yuri
858658768d version 2018-09-07 14:21:18 +03:00
yuri
86421010b9 fix meeting/call select manager 2018-09-07 14:20:01 +03:00
yuri
8675db36f3 stream sql optimization 2018-09-07 11:02:49 +03:00
yuri
f36a98a824 lead capture payload see more disabled 2018-09-06 15:21:45 +03:00
13 changed files with 170 additions and 60 deletions

View File

@@ -31,6 +31,18 @@ namespace Espo\Entities;
class Note extends \Espo\Core\ORM\Entity
{
private $aclIsProcessed = false;
public function setAclIsProcessed()
{
$this->aclIsProcessed = true;
}
public function isAclProcessed()
{
return $this->aclIsProcessed;
}
public function loadAttachments()
{
$data = $this->get('data');

View File

@@ -133,10 +133,19 @@ class Notifications extends \Espo\Core\Hooks\Base
$targetType = $parentType;
}
$teamIdList = $entity->getLinkMultipleIdList('teams');
$userIdList = $entity->getLinkMultipleIdList('users');
$skipAclCheck = false;
if (!$entity->isAclProcessed()) {
$skipAclCheck = true;
} else {
$teamIdList = $entity->getLinkMultipleIdList('teams');
$userIdList = $entity->getLinkMultipleIdList('users');
}
foreach ($userList as $user) {
if ($skipAclCheck) {
$notifyUserIdList[] = $user->id;
continue;
}
if ($user->isAdmin()) {
$notifyUserIdList[] = $user->id;
continue;

View File

@@ -34,6 +34,8 @@ use \Espo\ORM\Entity;
class Meeting extends \Espo\Core\Acl\Base
{
protected $ownerUserIdAttribute = 'usersIds';
public function checkEntityRead(User $user, Entity $entity, $data)
{
if ($this->checkEntity($user, $entity, $data, 'read')) {

View File

@@ -33,13 +33,14 @@ class Call extends \Espo\Core\SelectManagers\Base
{
protected function accessOnlyOwn(&$result)
{
$this->addJoin('users', $result);
$result['whereClause'][] = array(
'OR' => array(
'usersMiddle.userId' => $this->getUser()->id,
$this->setDistinct(true, $result);
$this->addJoin(['users', 'usersAccess'], $result);
$result['whereClause'][] = [
'OR' => [
'usersAccessMiddle.userId' => $this->getUser()->id,
'assignedUserId' => $this->getUser()->id
)
);
]
];
}
protected function accessOnlyTeam(&$result)
@@ -48,25 +49,25 @@ class Call extends \Espo\Core\SelectManagers\Base
$this->addLeftJoin(['teams', 'teamsAccess'], $result);
$this->addLeftJoin(['users', 'usersAccess'], $result);
$result['whereClause'][] = array(
'OR' => array(
'teamsAccess.id' => $this->getUser()->getLinkMultipleIdList('teams'),
'usersAccess.id' => $this->getUser()->id,
$result['whereClause'][] = [
'OR' => [
'teamsAccessMiddle.teamId' => $this->getUser()->getLinkMultipleIdList('teams'),
'usersAccessMiddle.userId' => $this->getUser()->id,
'assignedUserId' => $this->getUser()->id
)
);
]
];
}
protected function boolFilterOnlyMy(&$result)
{
$this->addJoin('users', $result);
$result['whereClause'][] = array(
'users.id' => $this->getUser()->id,
'OR' => array(
'usersMiddle.status!=' => 'Declined',
'usersMiddle.status=' => null
)
);
$this->addJoin(['users', 'usersFilterOnlyMy'], $result);
$result['whereClause'][] = [
'usersFilterOnlyMyMiddle.userId' => $this->getUser()->id,
'OR' => [
'usersFilterOnlyMyMiddle.status!=' => 'Declined',
'usersFilterOnlyMyMiddle.status=' => null
]
];
}
protected function filterPlanned(&$result)

View File

@@ -33,13 +33,14 @@ class Meeting extends \Espo\Core\SelectManagers\Base
{
protected function accessOnlyOwn(&$result)
{
$this->addJoin('users', $result);
$result['whereClause'][] = array(
'OR' => array(
'usersMiddle.userId' => $this->getUser()->id,
$this->setDistinct(true, $result);
$this->addJoin(['users', 'usersAccess'], $result);
$result['whereClause'][] = [
'OR' => [
'usersAccessMiddle.userId' => $this->getUser()->id,
'assignedUserId' => $this->getUser()->id
)
);
]
];
}
protected function accessOnlyTeam(&$result)
@@ -48,25 +49,25 @@ class Meeting extends \Espo\Core\SelectManagers\Base
$this->addLeftJoin(['teams', 'teamsAccess'], $result);
$this->addLeftJoin(['users', 'usersAccess'], $result);
$result['whereClause'][] = array(
'OR' => array(
'teamsAccess.id' => $this->getUser()->getLinkMultipleIdList('teams'),
'usersAccess.id' => $this->getUser()->id,
$result['whereClause'][] = [
'OR' => [
'teamsAccessMiddle.teamId' => $this->getUser()->getLinkMultipleIdList('teams'),
'usersAccessMiddle.userId' => $this->getUser()->id,
'assignedUserId' => $this->getUser()->id
)
);
]
];
}
protected function boolFilterOnlyMy(&$result)
{
$this->addJoin('users', $result);
$result['whereClause'][] = array(
'users.id' => $this->getUser()->id,
'OR' => array(
'usersMiddle.status!=' => 'Declined',
'usersMiddle.status=' => null
)
);
$this->addJoin(['users', 'usersFilterOnlyMy'], $result);
$result['whereClause'][] = [
'usersFilterOnlyMyMiddle.userId' => $this->getUser()->id,
'OR' => [
'usersFilterOnlyMyMiddle.status!=' => 'Declined',
'usersFilterOnlyMyMiddle.status=' => null
]
];
}
protected function filterPlanned(&$result)
@@ -92,4 +93,3 @@ class Meeting extends \Espo\Core\SelectManagers\Base
));
}
}

View File

@@ -44,7 +44,7 @@ class UniqueId extends \Espo\Core\ORM\Repositories\RDB
protected function getNewEntity()
{
$entity = parent::getNewEntity();
$entity->set('name', uniqid());
$entity->set('name', \Espo\Core\Utils\Util::generateId());
return $entity;
}
}

View File

@@ -84,7 +84,8 @@
"exampleRequestPayload": {
"type": "text",
"notStorable": true,
"readOnly": true
"readOnly": true,
"seeMoreDisabled": true
},
"createdAt": {
"type": "datetime",

View File

@@ -261,6 +261,7 @@ class App extends \Espo\Core\Services\Base
}
}
// TODO remove in 5.5.0
public function jobPopulateArrayValues()
{
$scopeList = array_keys($this->getMetadata()->get(['scopes']));
@@ -310,4 +311,75 @@ class App extends \Espo\Core\Services\Base
}
}
}
// TODO remove in 5.5.0
public function jobPopulateNotesTeamUser()
{
$aclManager = $this->getInjection('container')->get('aclManager');
$sql = $this->getEntityManager()->getQuery()->createSelectQuery('Note', [
'whereClause' => [
'parentId!=' => null,
'type=' => ['Relate', 'CreateRelated', 'EmailReceived', 'EmailSent', 'Assign', 'Create'],
],
'limit' => 100000,
'orderBy' => [['number', 'DESC']]
]);
$sth = $this->getEntityManager()->getPdo()->prepare($sql);
$sth->execute();
$i = 0;
while ($dataRow = $sth->fetch(\PDO::FETCH_ASSOC)) {
$i++;
$note = $this->getEntityManager()->getEntityFactory()->create('Note');
$note->set($dataRow);
$note->setAsFetched();
if ($note->get('relatedId') && $note->get('relatedType')) {
$targetType = $note->get('relatedType');
$targetId = $note->get('relatedId');
} else if ($note->get('parentId') && $note->get('parentType')) {
$targetType = $note->get('parentType');
$targetId = $note->get('parentId');
} else {
continue;
}
if (!$this->getEntityManager()->hasRepository($targetType)) continue;
try {
$entity = $this->getEntityManager()->getEntity($targetType, $targetId);
if (!$entity) continue;
$ownerUserIdAttribute = $aclManager->getImplementation($targetType)->getOwnerUserIdAttribute($entity);
$toSave = false;
if ($ownerUserIdAttribute) {
if ($entity->getAttributeParam($ownerUserIdAttribute, 'isLinkMultipleIdList')) {
$link = $entity->getAttributeParam($ownerUserIdAttribute, 'relation');
$userIdList = $entity->getLinkMultipleIdList($link);
} else {
$userId = $entity->get($ownerUserIdAttribute);
if ($userId) {
$userIdList = [$userId];
} else {
$userIdList = [];
}
}
if (!empty($userIdList)) {
$note->set('usersIds', $userIdList);
$toSave = true;
}
}
if ($entity->hasLinkMultipleField('teams')) {
$teamIdList = $entity->getLinkMultipleIdList('teams');
if (!empty($teamIdList)) {
$note->set('teamsIds', $teamIdList);
$toSave = true;
}
}
if ($toSave) {
$this->getEntityManager()->saveEntity($note);
}
} catch (\Exception $e) {}
}
}
}

View File

@@ -74,7 +74,7 @@ class Notification extends \Espo\Services\Record
$userId = $user->id;
if (!$this->checkUserNoteAccess($user, $note)) continue;
if ($note->get('createdById') === $user->id) continue;
$id = uniqid();
$id = \Espo\Core\Utils\Util::generateId();
$arr[] = "(".$query->quote($id).", ".$query->quote($encodedData).", ".$query->quote('Note').", ".$query->quote($userId).", ".$query->quote($now).", ".$query->quote($note->id).", ".$query->quote('Note').", ".$query->quote($note->get('parentId')).", ".$query->quote($note->get('parentType')).")";
}

View File

@@ -384,8 +384,8 @@ class Stream extends \Espo\Core\Services\Base
if (count($onlyTeamEntityTypeList)) {
$selectParamsSubscriptionTeam = $selectParamsSubscription;
$selectParamsSubscriptionTeam['distinct'] = true;
$selectParamsSubscriptionTeam['leftJoins'][] = 'teams';
$selectParamsSubscriptionTeam['leftJoins'][] = 'users';
$selectParamsSubscriptionTeam['leftJoins'][] = ['noteTeam', 'noteTeam', ['noteTeam.noteId=:' => 'id', 'noteTeam.deleted' => false]];
$selectParamsSubscriptionTeam['leftJoins'][] = ['noteUser', 'noteUser', ['noteUser.noteId=:' => 'id', 'noteUser.deleted' => false]];
$selectParamsSubscriptionTeam['whereClause'][] = [
[
'relatedId!=' => null,
@@ -393,8 +393,8 @@ class Stream extends \Espo\Core\Services\Base
],
[
'OR' => [
'teamsMiddle.teamId' => $teamIdList,
'usersMiddle.userId' => $user->id
'noteTeam.teamId' => $teamIdList,
'noteUser.userId' => $user->id
]
]
];
@@ -404,13 +404,13 @@ class Stream extends \Espo\Core\Services\Base
if (count($onlyOwnEntityTypeList)) {
$selectParamsSubscriptionOwn = $selectParamsSubscription;
$selectParamsSubscriptionOwn['distinct'] = true;
$selectParamsSubscriptionOwn['leftJoins'][] = 'users';
$selectParamsSubscriptionOwn['leftJoins'][] = ['noteUser', 'noteUser', ['noteUser.noteId=:' => 'id', 'noteUser.deleted' => false]];
$selectParamsSubscriptionOwn['whereClause'][] = [
[
'relatedId!=' => null,
'relatedType=' => $onlyOwnEntityTypeList
],
'usersMiddle.userId' => $user->id
'noteUser.userId' => $user->id
];
$selectParamsList[] = $selectParamsSubscriptionOwn;
}
@@ -461,8 +461,8 @@ class Stream extends \Espo\Core\Services\Base
if (count($onlyTeamEntityTypeList)) {
$selectParamsSubscriptionTeam = $selectParamsSubscriptionSuper;
$selectParamsSubscriptionTeam['distinct'] = true;
$selectParamsSubscriptionTeam['leftJoins'][] = 'teams';
$selectParamsSubscriptionTeam['leftJoins'][] = 'users';
$selectParamsSubscriptionTeam['leftJoins'][] = ['noteTeam', 'noteTeam', ['noteTeam.noteId=:' => 'id', 'noteTeam.deleted' => false]];
$selectParamsSubscriptionTeam['leftJoins'][] = ['noteUser', 'noteUser', ['noteUser.noteId=:' => 'id', 'noteUser.deleted' => false]];
$selectParamsSubscriptionTeam['whereClause'][] = [
'OR' => [
[
@@ -476,8 +476,8 @@ class Stream extends \Espo\Core\Services\Base
],
[
'OR' => [
'teamsMiddle.teamId' => $teamIdList,
'usersMiddle.userId' => $user->id
'noteTeam.teamId' => $teamIdList,
'noteUser.userId' => $user->id
]
]
];
@@ -487,7 +487,7 @@ class Stream extends \Espo\Core\Services\Base
if (count($onlyOwnEntityTypeList)) {
$selectParamsSubscriptionOwn = $selectParamsSubscriptionSuper;
$selectParamsSubscriptionOwn['distinct'] = true;
$selectParamsSubscriptionOwn['leftJoins'][] = 'users';
$selectParamsSubscriptionOwn['leftJoins'][] = ['noteUser', 'noteUser', ['noteUser.noteId=:' => 'id', 'noteUser.deleted' => false]];
$selectParamsSubscriptionOwn['whereClause'][] = [
'OR' => [
[
@@ -499,7 +499,7 @@ class Stream extends \Espo\Core\Services\Base
'parentType=' => $onlyOwnEntityTypeList
]
],
'usersMiddle.userId' => $user->id
'noteUser.userId' => $user->id
];
$selectParamsList[] = $selectParamsSubscriptionOwn;
}
@@ -889,6 +889,10 @@ class Stream extends \Espo\Core\Services\Base
protected function processNoteTeamsUsers(Entity $note, Entity $entity)
{
$note->setAclIsProcessed();
$note->set('teamsIds', []);
$note->set('usersIds', []);
if ($entity->hasLinkMultipleField('teams') && $entity->has('teamsIds')) {
$teamIdList = $entity->get('teamsIds');
if (!empty($teamIdList)) {

View File

@@ -20,7 +20,7 @@
<tr class="kanban-row">
{{#each groupDataList}}
<th data-name="{{name}}" class="group-header">
<div>{{label}}</div>
<div><span class="kanban-group-label">{{label}}</span></div>
</th>
{{/each}}
</tr>

View File

@@ -309,6 +309,15 @@ div.list-kanban > div.kanban-columns-container {
overflow: hidden;
> th {
overflow: visible;
min-width: 0;
max-height: 28px;
.kanban-group-label {
display: inline-block;
max-width: ~"calc(100% - 15px)";
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
}
}
}

View File

@@ -1,6 +1,6 @@
{
"name": "espocrm",
"version": "5.4.0",
"version": "5.4.2",
"description": "",
"main": "index.php",
"repository": {