diff --git a/application/Espo/Core/ServiceFactory.php b/application/Espo/Core/ServiceFactory.php
index fd38987532..963a69ce03 100644
--- a/application/Espo/Core/ServiceFactory.php
+++ b/application/Espo/Core/ServiceFactory.php
@@ -67,13 +67,10 @@ class ServiceFactory
protected function getClassName($name)
{
- $name = Util::normilizeClassName($name);
-
if (!isset($this->data)) {
$this->init();
}
- $name = ucfirst($name);
if (isset($this->data[$name])) {
return $this->data[$name];
}
diff --git a/application/Espo/EntryPoints/Download.php b/application/Espo/EntryPoints/Download.php
index a2660b1ca2..a631f7bf64 100644
--- a/application/Espo/EntryPoints/Download.php
+++ b/application/Espo/EntryPoints/Download.php
@@ -18,7 +18,7 @@
*
* You should have received a copy of the GNU General Public License
* along with EspoCRM. If not, see http://www.gnu.org/licenses/.
- ************************************************************************/
+ ************************************************************************/
namespace Espo\EntryPoints;
@@ -29,45 +29,49 @@ use \Espo\Core\Exceptions\BadRequest;
class Download extends \Espo\Core\EntryPoints\Base
{
public static $authRequired = true;
-
+
protected $fileTypesToShowInline = array(
'application/pdf',
+ 'application/vnd.ms-word',
+ 'application/vnd.ms-excel',
+ 'application/vnd.oasis.opendocument.text',
+ 'application/vnd.oasis.opendocument.spreadsheet',
+ 'text/plain',
);
-
+
public function run()
- {
+ {
$id = $_GET['id'];
if (empty($id)) {
throw new BadRequest();
}
-
+
$attachment = $this->getEntityManager()->getEntity('Attachment', $id);
-
+
if (!$attachment) {
throw new NotFound();
- }
-
+ }
+
if ($attachment->get('parentId') && $attachment->get('parentType')) {
- $parent = $this->getEntityManager()->getEntity($attachment->get('parentType'), $attachment->get('parentId'));
+ $parent = $this->getEntityManager()->getEntity($attachment->get('parentType'), $attachment->get('parentId'));
if (!$this->getAcl()->check($parent)) {
throw new Forbidden();
}
}
-
+
$fileName = "data/upload/{$attachment->id}";
-
+
if (!file_exists($fileName)) {
throw new NotFound();
}
-
+
$type = $attachment->get('type');
-
+
$disposition = 'attachment';
if (in_array($type, $this->fileTypesToShowInline)) {
$disposition = 'inline';
}
-
-
+
header('Content-Description: File Transfer');
if ($type) {
header('Content-Type: ' . $type);
@@ -80,7 +84,7 @@ class Download extends \Espo\Core\EntryPoints\Base
ob_clean();
flush();
readfile($fileName);
- exit;
- }
+ exit;
+ }
}
diff --git a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Reminder.json b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Reminder.json
index 199c6d9a65..c907e5998d 100644
--- a/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Reminder.json
+++ b/application/Espo/Modules/Crm/Resources/metadata/entityDefs/Reminder.json
@@ -17,7 +17,7 @@
},
"seconds": {
"type": "enumInt",
- "options": [0, 60, 120, 300, 900, 1800, 3600, 7200, 10800, 18000, 86400],
+ "options": [0, 60, 120, 300, 600, 900, 1800, 3600, 7200, 10800, 18000, 86400],
"default": 0
},
"entityType": {
diff --git a/application/Espo/Modules/Crm/Services/CaseObj.php b/application/Espo/Modules/Crm/Services/CaseObj.php
index 111865649b..1d41fe9452 100644
--- a/application/Espo/Modules/Crm/Services/CaseObj.php
+++ b/application/Espo/Modules/Crm/Services/CaseObj.php
@@ -26,7 +26,6 @@ use \Espo\ORM\Entity;
class CaseObj extends \Espo\Services\Record
{
-
protected $mergeLinkList = array(
'tasks',
'meetings',
diff --git a/application/Espo/Resources/i18n/en_US/Global.json b/application/Espo/Resources/i18n/en_US/Global.json
index 906b6082b4..aac87ab56f 100644
--- a/application/Espo/Resources/i18n/en_US/Global.json
+++ b/application/Espo/Resources/i18n/en_US/Global.json
@@ -44,6 +44,7 @@
"Uploading...": "Uploading...",
"Sending...": "Sending...",
"Merging...": "Merging...",
+ "Merged": "Merged",
"Removed": "Removed",
"Posted": "Posted",
"Linked": "Linked",
diff --git a/application/Espo/Resources/metadata/scopes/User.json b/application/Espo/Resources/metadata/scopes/User.json
index 38a0ecc2bc..40469e6b74 100644
--- a/application/Espo/Resources/metadata/scopes/User.json
+++ b/application/Espo/Resources/metadata/scopes/User.json
@@ -1 +1,7 @@
-{"entity":true,"layouts":true,"tab":false,"acl":false,"customizable":true}
+{
+ "entity": true,
+ "layouts": true,
+ "tab": true,
+ "acl": false,
+ "customizable": true
+}
diff --git a/application/Espo/Services/Record.php b/application/Espo/Services/Record.php
index c6ba7e0a14..de07006aa5 100644
--- a/application/Espo/Services/Record.php
+++ b/application/Espo/Services/Record.php
@@ -72,7 +72,7 @@ class Record extends \Espo\Core\Services\Base
$name = $matches[1];
}
if ($name != 'Record') {
- $this->entityName = $name;
+ $this->entityName = Util::normilizeScopeName($name);
}
}
}
@@ -763,8 +763,7 @@ class Record extends \Espo\Core\Services\Base
UPDATE `note`
SET
`parent_id` = " . $pdo->quote($entity->id) . ",
- `parent_type` = " . $pdo->quote($entity->getEntityName()) . ",
-
+ `parent_type` = " . $pdo->quote($entity->getEntityName()) . "
WHERE
`type` IN ('Post', 'EmailSent', 'EmailReceived') AND
`parent_id` = " . $pdo->quote($source->id) . " AND
@@ -774,16 +773,18 @@ class Record extends \Espo\Core\Services\Base
$pdo->query($sql);
}
+ $repository = $this->getEntityManager()->getRepository($entity->getEntityName());
+
foreach ($sourceList as $source) {
foreach ($this->mergeLinkList as $link) {
- $linkedList = $this->getEntityManager()->getRepository($this->name)->findRelated($source, $link);
+ $linkedList = $repository->findRelated($source, $link);
foreach ($linkedList as $linked) {
- $this->getEntityManager()->getRepository()->relate($entity, $link, $linked);
- $this->getEntityManager()->getRepository()->unrelate($source, $link, $linked);
+ $repository->relate($entity, $link, $linked);
}
}
}
+
foreach ($sourceList as $source) {
$this->getEntityManager()->removeEntity($source);
}
diff --git a/frontend/client/modules/crm/src/views/meeting/fields/reminders.js b/frontend/client/modules/crm/src/views/meeting/fields/reminders.js
index 8a282e3fc3..7d34ea1ac6 100644
--- a/frontend/client/modules/crm/src/views/meeting/fields/reminders.js
+++ b/frontend/client/modules/crm/src/views/meeting/fields/reminders.js
@@ -22,7 +22,7 @@
Espo.define('Crm:Views.Meeting.Fields.Reminders', 'Views.Fields.Base', function (Dep) {
return Dep.extend({
-
+
detailTemplate: 'crm:meeting.fields.reminders.detail',
listTemplate: 'crm:meeting.fields.reminders.detail',
@@ -33,7 +33,7 @@ Espo.define('Crm:Views.Meeting.Fields.Reminders', 'Views.Fields.Base', function
'click [data-action="addReminder"]': function () {
var type = this.getMetadata().get('entityDefs.Reminder.fields.type.default');
var seconds = this.getMetadata().get('entityDefs.Reminder.fields.seconds.default');
-
+
var item = {
type: type,
seconds: seconds
@@ -66,7 +66,7 @@ Espo.define('Crm:Views.Meeting.Fields.Reminders', 'Views.Fields.Base', function
}, this);
this.typeList = this.getMetadata().get('entityDefs.Reminder.fields.type.options');
- this.secondsList = this.getMetadata().get('entityDefs.Reminder.fields.seconds.options');;
+ this.secondsList = this.getMetadata().get('entityDefs.Reminder.fields.seconds.options');
},
afterRender: function () {
diff --git a/frontend/client/res/templates/fields/url/detail.tpl b/frontend/client/res/templates/fields/url/detail.tpl
index c9d6d662d6..4ff7c7f725 100644
--- a/frontend/client/res/templates/fields/url/detail.tpl
+++ b/frontend/client/res/templates/fields/url/detail.tpl
@@ -1 +1 @@
-{{value}}
+{{value}}
diff --git a/frontend/client/src/views/admin/extensions/index.js b/frontend/client/src/views/admin/extensions/index.js
index c428716fb8..dc4e4ae853 100644
--- a/frontend/client/src/views/admin/extensions/index.js
+++ b/frontend/client/src/views/admin/extensions/index.js
@@ -17,16 +17,16 @@
*
* You should have received a copy of the GNU General Public License
* along with EspoCRM. If not, see http://www.gnu.org/licenses/.
- ************************************************************************/
+ ************************************************************************/
-Espo.define('Views.Admin.Extensions.Index', 'View', function (Dep) {
+Espo.define('Views.Admin.Extensions.Index', 'View', function (Dep) {
return Dep.extend({
-
+
template: "admin.extensions.index",
-
+
packageContents: null,
-
+
events: {
'change input[name="package"]': function (e) {
this.$el.find('button[data-action="upload"]').addClass('disabled');
@@ -41,22 +41,22 @@ Espo.define('Views.Admin.Extensions.Index', 'View', function (Dep) {
},
'click [data-action="install"]': function (e) {
var id = $(e.currentTarget).data('id');
-
+
var name = this.collection.get(id).get('name');
var version = this.collection.get(id).get('version');
-
+
this.run(id, name, version);
-
+
},
'click [data-action="uninstall"]': function (e) {
var id = $(e.currentTarget).data('id');
-
+
var name = this.collection.get(id).get('name');
-
+
var self = this;
- if (confirm(this.translate('uninstallConfirmation', 'messages', 'Admin'))) {
+ if (confirm(this.translate('uninstallConfirmation', 'messages', 'Admin'))) {
Espo.Ui.notify(this.translate('Uninstalling...', 'labels', 'Admin'));
-
+
$.ajax({
url: 'Extension/action/uninstall',
type: 'POST',
@@ -67,25 +67,25 @@ Espo.define('Views.Admin.Extensions.Index', 'View', function (Dep) {
var msg = xhr.getResponseHeader('X-Status-Reason');
this.showErrorNotification(this.translate('Error') + ': ' + msg);
}.bind(this)
- }).done(function () {
+ }).done(function () {
this.listenToOnce(this.collection, 'sync', function () {
Espo.Ui.success(this.translate('uninstalled', 'messages', 'Extension').replace('{name}', name));
}, this);
this.collection.fetch();
-
+
}.bind(this));
}
}
},
-
+
setup: function () {
this.getCollectionFactory().create('Extension', function (collection) {
this.collection = collection;
-
+
collection.maxSize = this.getConfig().get('recordsPerPage');
-
+
this.wait(true);
- this.listenToOnce(collection, 'sync', function () {
+ this.listenToOnce(collection, 'sync', function () {
this.createView('list', 'Extension.Record.List', {
collection: collection,
el: this.options.el + ' > .list-container',
@@ -97,36 +97,36 @@ Espo.define('Views.Admin.Extensions.Index', 'View', function (Dep) {
}
this.wait(false);
});
-
+
collection.fetch();
-
+
}, this);
},
-
+
selectFile: function (file) {
var fileReader = new FileReader();
- fileReader.onload = function (e) {
+ fileReader.onload = function (e) {
this.packageContents = e.target.result;
this.$el.find('button[data-action="upload"]').removeClass('disabled');
}.bind(this);
fileReader.readAsDataURL(file);
},
-
+
showError: function (msg) {
msg = this.translate(msg, 'errors', 'Admin');
this.$el.find('.message-container').html(msg);
},
-
+
showErrorNotification: function (msg) {
if (!msg) {
this.$el.find('.notify-text').addClass('hidden');
- } else {
+ } else {
msg = this.translate(msg, 'errors', 'Admin');
this.$el.find('.notify-text').html(msg);
this.$el.find('.notify-text').removeClass('hidden');
}
},
-
+
upload: function () {
this.$el.find('button[data-action="upload"]').addClass('disabled');
this.notify('Uploading...');
@@ -134,9 +134,9 @@ Espo.define('Views.Admin.Extensions.Index', 'View', function (Dep) {
url: 'Extension/action/upload',
type: 'POST',
contentType: 'application/zip',
- timeout: 0,
+ timeout: 0,
data: this.packageContents,
- error: function (xhr, t, e) {
+ error: function (xhr, t, e) {
this.showError(xhr.getResponseHeader('X-Status-Reason'));
this.notify(false);
}.bind(this)
@@ -151,23 +151,23 @@ Espo.define('Views.Admin.Extensions.Index', 'View', function (Dep) {
}, function (view) {
view.render();
this.$el.find('button[data-action="upload"]').removeClass('disabled');
-
+
view.once('run', function () {
view.close();
this.$el.find('.panel.upload').addClass('hidden');
this.run(data.id, data.version, data.name);
}, this);
- }.bind(this));
+ }.bind(this));
}.bind(this)).error;
- },
-
- run: function (id, version, name) {
+ },
+
+ run: function (id, version, name) {
var msg = this.translate('Installing...', 'labels', 'Admin');
this.notify('Please wait...');
-
+
this.showError(false);
- this.showErrorNotification(false);
-
+ this.showErrorNotification(false);
+
$.ajax({
url: 'Extension/action/install',
type: 'POST',
@@ -178,26 +178,26 @@ Espo.define('Views.Admin.Extensions.Index', 'View', function (Dep) {
this.$el.find('.panel.upload').removeClass('hidden');
var msg = xhr.getResponseHeader('X-Status-Reason');
this.showErrorNotification(this.translate('Error') + ': ' + msg);
- }.bind(this)
+ }.bind(this)
}).done(function () {
var cache = this.getCache();
if (cache) {
- cache.clear();
+ cache.clear();
}
this.createView('popup', 'Admin.Extensions.Done', {
version: version,
name: name
}, function (view) {
this.collection.fetch();
- this.$el.find('.list-container').removeClass('hidden');
- this.$el.find('.panel.upload').removeClass('hidden');
+ this.$el.find('.list-container').removeClass('hidden');
+ this.$el.find('.panel.upload').removeClass('hidden');
this.notify(false);
- view.render();
+ view.render();
}.bind(this));
}.bind(this));
},
-
- });
-
+
+ });
+
});
diff --git a/frontend/client/src/views/admin/upgrade/index.js b/frontend/client/src/views/admin/upgrade/index.js
index dbc5cfb92d..c59852dd6f 100644
--- a/frontend/client/src/views/admin/upgrade/index.js
+++ b/frontend/client/src/views/admin/upgrade/index.js
@@ -17,14 +17,14 @@
*
* You should have received a copy of the GNU General Public License
* along with EspoCRM. If not, see http://www.gnu.org/licenses/.
- ************************************************************************/
+ ************************************************************************/
Espo.define('Views.Admin.Upgrade.Index', 'View', function (Dep) {
return Dep.extend({
template: 'admin.upgrade.index',
-
+
packageContents: null,
data: function () {
@@ -50,21 +50,21 @@ Espo.define('Views.Admin.Upgrade.Index', 'View', function (Dep) {
setup: function () {
},
-
+
selectFile: function (file) {
var fileReader = new FileReader();
- fileReader.onload = function (e) {
+ fileReader.onload = function (e) {
this.packageContents = e.target.result;
this.$el.find('button[data-action="upload"]').removeClass('disabled');
}.bind(this);
fileReader.readAsDataURL(file);
},
-
+
showError: function (msg) {
msg = this.translate(msg, 'errors', 'Admin');
this.$el.find('.message-container').html(msg);
},
-
+
upload: function () {
this.$el.find('button[data-action="upload"]').addClass('disabled');
this.notify('Uploading...');
@@ -72,11 +72,11 @@ Espo.define('Views.Admin.Upgrade.Index', 'View', function (Dep) {
url: 'Admin/action/uploadUpgradePackage',
type: 'POST',
contentType: 'application/zip',
- timeout: 0,
+ timeout: 0,
data: this.packageContents,
- error: function (xhr, t, e) {
+ error: function (xhr, t, e) {
this.showError(xhr.getResponseHeader('X-Status-Reason'));
- this.notify(false);
+ this.notify(false);
}.bind(this)
}).done(function (data) {
if (!data.id) {
@@ -89,25 +89,25 @@ Espo.define('Views.Admin.Upgrade.Index', 'View', function (Dep) {
}, function (view) {
view.render();
this.$el.find('button[data-action="upload"]').removeClass('disabled');
-
+
view.once('run', function () {
view.close();
this.$el.find('.panel.upload').addClass('hidden');
this.run(data.id, data.version);
}, this);
- }.bind(this));
+ }.bind(this));
}.bind(this)).error;
},
-
+
textNotification: function (text) {
- this.$el.find('.notify-text').html(text);
+ this.$el.find('.notify-text').html(text);
},
-
- run: function (id, version) {
+
+ run: function (id, version) {
var msg = this.translate('Upgrading...', 'labels', 'Admin');
this.notify('Please wait...');
- this.textNotification(msg);
-
+ this.textNotification(msg);
+
$.ajax({
url: 'Admin/action/runUpgrade',
type: 'POST',
@@ -118,17 +118,17 @@ Espo.define('Views.Admin.Upgrade.Index', 'View', function (Dep) {
this.$el.find('.panel.upload').removeClass('hidden');
var msg = xhr.getResponseHeader('X-Status-Reason');
this.textNotification(this.translate('Error') + ': ' + msg);
- }.bind(this)
+ }.bind(this)
}).done(function () {
var cache = this.getCache();
if (cache) {
- cache.clear();
+ cache.clear();
}
this.createView('popup', 'Admin.Upgrade.Done', {
version: version
}, function (view) {
this.notify(false);
- view.render();
+ view.render();
}.bind(this));
}.bind(this));
},
diff --git a/frontend/client/src/views/record/merge.js b/frontend/client/src/views/record/merge.js
index 3db66ffea1..8ef426e776 100644
--- a/frontend/client/src/views/record/merge.js
+++ b/frontend/client/src/views/record/merge.js
@@ -108,26 +108,11 @@ Espo.define('Views.Record.Merge', 'View', function (Dep) {
})
})
}).done(function () {
- return;
model.once('sync', function () {
this.notify('Merged', 'success');
this.getRouter().navigate('#' + this.scope + '/view/' + model.id, {trigger: true});
- /*var i = 0;
- var count = this.models.length;
- this.models.forEach(function (m) {
- if (m.id != model.id) {
- m.once('destroy', function () {
- i++;
- if (i == count - 1) {
- this.notify('Merged', 'success');
- this.getRouter().navigate('#' + this.scope + '/view/' + model.id, {trigger: true});
- }
- }, this);
- m.destroy();
- }
- }, this);*/
}, this);
model.save(attributes, {