admin changes update current and other tabs

This commit is contained in:
Yuri Kuznetsov
2021-06-30 12:55:07 +03:00
parent d67ebbe683
commit 8c43d3f378
13 changed files with 257 additions and 68 deletions

View File

@@ -58,6 +58,7 @@ define(
'ajax',
'number',
'page-title',
'broadcast-channel'
],
function (
Espo,
@@ -88,7 +89,8 @@ define(
WebSocketManager,
Ajax,
NumberUtil,
PageTitle
PageTitle,
BroadcastChannel
) {
let App = function (options, callback) {
@@ -149,6 +151,8 @@ define(
responseCache: null,
broadcastChannel: null,
initCache: function (options) {
let cacheTimestamp = options.cacheTimestamp || null;
let storedCacheTimestamp = null;
@@ -290,6 +294,8 @@ define(
this.webSocketManager.connect(this.auth, this.user.id);
}
this.initBroadcastChannel();
let promiseList = [];
let aclImplementationClassMap = {};
@@ -426,6 +432,7 @@ define(
storage: this.storage,
metadata: this.metadata,
dateTime: this.dateTime,
broadcastChannel: this.broadcastChannel,
};
},
@@ -649,14 +656,17 @@ define(
this.unsetCookieAuth();
if (this.broadcastChannel.object) {
this.broadcastChannel.object.close();
}
this.broadcastChannel = null;
xhr = new XMLHttpRequest;
xhr.open('GET', this.basePath + this.apiUrl + '/');
xhr.setRequestHeader('Authorization', 'Basic ' + base64.encode('**logout:logout'));
xhr.send('');
xhr.abort();
this.loadStylesheet();
@@ -884,6 +894,37 @@ define(
});
},
initBroadcastChannel: function () {
this.broadcastChannel = new BroadcastChannel();
this.broadcastChannel.subscribe(event => {
if (event.data === 'update:all') {
this.metadata.loadSkipCache();
this.settings.loadSkipCache();
this.language.loadSkipCache();
this.viewHelper.layoutManager.clearLoadedData();
}
if (event.data === 'update:metadata') {
this.metadata.loadSkipCache();
}
if (event.data === 'update:config') {
this.settings.load();
}
if (event.data === 'update:language') {
this.language.loadSkipCache();
}
if (event.data === 'update:layout') {
this.viewHelper.layoutManager.clearLoadedData();
}
});
this.viewHelper.broadcastChannel = this.broadcastChannel;
},
}, Backbone.Events);
App.extend = Backbone.Router.extend;

View File

@@ -0,0 +1,58 @@
/************************************************************************
* This file is part of EspoCRM.
*
* EspoCRM - Open Source CRM application.
* Copyright (C) 2014-2021 Yurii Kuznietsov, Taras Machyshyn, Oleksii Avramenko
* Website: https://www.espocrm.com
*
* EspoCRM is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* EspoCRM is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with EspoCRM. If not, see http://www.gnu.org/licenses/.
*
* The interactive user interfaces in modified source and object code versions
* of this program must display Appropriate Legal Notices, as required under
* Section 5 of the GNU General Public License version 3.
*
* In accordance with Section 7(b) of the GNU General Public License version 3,
* these Appropriate Legal Notices must retain the display of the "EspoCRM" word.
************************************************************************/
define('broadcast-channel', [], function () {
let Channel = class {
constructor() {
this.object = null;
if (BroadcastChannel) {
this.object = new BroadcastChannel('app');
}
}
postMessage(message) {
if (!this.object) {
return;
}
this.object.postMessage(message);
}
subscribe(callback) {
if (!this.object) {
return;
}
this.object.addEventListener('message', callback);
}
};
return Channel;
});

View File

@@ -50,6 +50,7 @@ define('controller', [], function () {
this._storage = injections.storage || null;
this._metadata = injections.metadata || null;
this._dateTime = injections.dateTime || null;
this._broadcastChannel = injections.broadcastChannel || null;
this.set('masterRendered', false);
};

View File

@@ -116,6 +116,12 @@ define('controllers/admin', ['controller', 'search-manager'], function (Dep, Sea
let model = this.getConfig().clone();
model.defs = this.getConfig().defs;
this.listenTo(model, 'after:save', () => {
this.getConfig().load();
this._broadcastChannel.postMessage('update:config');
});
return model;
},

View File

@@ -176,6 +176,10 @@ define('layout-manager', [], function () {
);
},
clearLoadedData: function () {
this.data = {};
},
}, Backbone.Events);
return LayoutManager;

View File

@@ -705,6 +705,8 @@ define('views/admin/entity-manager/modals/edit-entity', ['views/modal', 'model']
scope: name,
};
this.broadcastUpdate();
this.trigger('after:save', o);
});
})
@@ -731,6 +733,8 @@ define('views/admin/entity-manager/modals/edit-entity', ['views/modal', 'model']
this.model.fetchedAttributes = this.model.getClonedAttributes();
this.notify('Done', 'success');
this.broadcastUpdate();
});
});
});
@@ -827,5 +831,11 @@ define('views/admin/entity-manager/modals/edit-entity', ['views/modal', 'model']
return filtersOptionList;
},
broadcastUpdate: function () {
this.getHelper().broadcastChannel.postMessage('update:metadata');
this.getHelper().broadcastChannel.postMessage('update:language');
this.getHelper().broadcastChannel.postMessage('update:config');
},
});
});

View File

@@ -148,6 +148,8 @@ define('views/admin/entity-manager/scope', 'view', function (Dep) {
this.getConfig().load().then(() => {
Espo.Ui.notify(false);
this.broadcastUpdate();
this.getRouter().navigate('#Admin/entityManager', {trigger: true});
});
});
@@ -195,5 +197,10 @@ define('views/admin/entity-manager/scope', 'view', function (Dep) {
this.$el.find('.item-dropdown-button"]').removeClass('disabled').removeAttr('disabled');
},
broadcastUpdate: function () {
this.getHelper().broadcastChannel.postMessage('update:metadata');
this.getHelper().broadcastChannel.postMessage('update:settings');
},
});
});

View File

@@ -565,6 +565,8 @@ define('views/admin/field-manager/edit', ['view', 'model'], function (Dep, Model
.then(() => this.trigger('after:save'));
this.model.fetchedAttributes = this.model.getClonedAttributes();
this.broadcastUpdate();
});
this.notify('Saving...');
@@ -648,6 +650,8 @@ define('views/admin/field-manager/edit', ['view', 'model'], function (Dep, Model
this.notify('Done', 'success');
this.reRender();
this.broadcastUpdate();
});
});
});
@@ -655,5 +659,11 @@ define('views/admin/field-manager/edit', ['view', 'model'], function (Dep, Model
}, this);
},
broadcastUpdate: function () {
this.getHelper().broadcastChannel.postMessage('update:metadata');
this.getHelper().broadcastChannel.postMessage('update:language');
this.getHelper().broadcastChannel.postMessage('update:settings');
},
});
});

View File

@@ -36,7 +36,7 @@ define('views/admin/field-manager/list', 'view', function (Dep) {
return {
scope: this.scope,
fieldDefsArray: this.fieldDefsArray,
typeList: this.typeList
typeList: this.typeList,
};
},
@@ -57,22 +57,26 @@ define('views/admin/field-manager/list', 'view', function (Dep) {
},
buildFieldDefs: function () {
return this.getModelFactory().create(this.scope).then(
function (model) {
this.fields = model.defs.fields;
this.fieldList = Object.keys(this.fields).sort();
this.fieldDefsArray = [];
this.fieldList.forEach(function (field) {
var defs = this.fields[field];
if (defs.customizationDisabled) return;
this.fieldDefsArray.push({
name: field,
isCustom: defs.isCustom || false,
type: defs.type
});
}, this);
}.bind(this)
);
return this.getModelFactory().create(this.scope).then(model => {
this.fields = model.defs.fields;
this.fieldList = Object.keys(this.fields).sort();
this.fieldDefsArray = [];
this.fieldList.forEach(field => {
var defs = this.fields[field];
if (defs.customizationDisabled) {
return;
}
this.fieldDefsArray.push({
name: field,
isCustom: defs.isCustom || false,
type: defs.type,
});
});
});
},
removeField: function (field) {
@@ -87,15 +91,24 @@ define('views/admin/field-manager/list', 'view', function (Dep) {
delete data['entityDefs'][this.scope]['fields'][field];
this.getMetadata().loadSkipCache(() => {
this.getMetadata().loadSkipCache().then(() =>
this.buildFieldDefs()
.then(() => {
this.broadcastUpdate();
return this.reRender();
})
.then(() => Espo.Ui.success(this.translate('Removed')));
});
.then(() =>
Espo.Ui.success(this.translate('Removed'))
)
);
});
});
},
broadcastUpdate: function () {
this.getHelper().broadcastChannel.postMessage('update:metadata');
this.getHelper().broadcastChannel.postMessage('update:language');
},
});
});

View File

@@ -134,8 +134,9 @@ define('views/admin/label-manager/edit', 'view', function (Dep) {
this.ajaxPostRequest('LabelManager/action/saveLabels', {
scope: this.scope,
language: this.language,
labels: data
}).then(returnData => {
labels: data,
})
.then(returnData => {
this.scopeDataInitial = Espo.Utils.cloneDeep(this.scopeData);
this.dirtyLabelList = [];
this.setConfirmLeaveOut(false);
@@ -149,7 +150,12 @@ define('views/admin/label-manager/edit', 'view', function (Dep) {
}
Espo.Ui.success(this.translate('Saved'));
}).fail(() => {
this.getHelper().broadcastChannel.postMessage('update:language');
this.getLanguage().loadSkipCache();
})
.fail(() => {
this.$save.removeClass('disabled').removeAttr('disabled');
this.$cancel.removeClass('disabled').removeAttr('disabled');
});

View File

@@ -109,6 +109,8 @@ define('views/admin/layouts/base', 'view', function (Dep) {
if (typeof callback === 'function') {
callback();
}
this.getHelper().broadcastChannel.postMessage('update:layout');
}, this.setId);
},

View File

@@ -746,6 +746,8 @@ define('views/admin/link-manager/modals/edit',
}
this.getMetadata().loadSkipCache().then(() => {
this.broadcastUpdate();
this.trigger('after:save');
this.close();
});
@@ -759,8 +761,13 @@ define('views/admin/link-manager/modals/edit',
var linkDefs = this.getMetadata().get(['entityDefs', item, 'links']) || {};
var isFound = false;
for (var i in linkDefs) {
if (linkDefs[i].foreign == link && linkDefs[i].entity == entityType && linkDefs[i].type === 'hasChildren') {
if (
linkDefs[i].foreign === link &&
linkDefs[i].entity === entityType &&
linkDefs[i].type === 'hasChildren'
) {
if (onlyNotCustom) {
if (linkDefs[i].isCustom) {
continue;
@@ -778,5 +785,10 @@ define('views/admin/link-manager/modals/edit',
return list;
},
broadcastUpdate: function () {
this.getHelper().broadcastChannel.postMessage('update:metadata');
this.getHelper().broadcastChannel.postMessage('update:language');
},
});
});

View File

@@ -357,38 +357,47 @@ define('views/site/navbar', 'view', function (Dep) {
this.getRouter().on('routed', (e) => {
if (e.controller) {
this.selectTab(e.controller);
return;
}
else {
this.selectTab(false);
}
this.selectTab(false);
});
var tabList = this.getTabList();
this.createView('notificationsBadge', 'views/notification/badge', {
el: this.options.el + ' .notifications-badge-container'
});
let setup = () => {
this.setupQuickCreateList();
this.setupGlobalSearch();
this.setupTabDefsList();
};
setup();
this.listenTo(this.getHelper().settings, 'sync', () => {
setup();
this.reRender();
});
this.listenTo(this.getHelper().language, 'sync', () => {
setup();
this.reRender();
});
this.once('remove', () => {
$(window).off('resize.navbar');
$(window).off('scroll.navbar');
$(window).off('scroll.navbar-tab-group');
});
},
setupQuickCreateList: function () {
var scopes = this.getMetadata().get('scopes') || {};
this.tabList = tabList.filter(item => {
if (!item) {
return false;
}
if (typeof item === 'object') {
item.itemList = item.itemList || [];
item.itemList = item.itemList.filter(item => {
return this.filterTabItem(item);
});
if (!item.itemList.length) {
return false;
}
return true;
}
return this.filterTabItem(item);
});
this.quickCreateList = this.getQuickCreateList().filter(scope =>{
if (!scopes[scope]) {
return false;
@@ -404,20 +413,6 @@ define('views/site/navbar', 'view', function (Dep) {
return true;
});
this.createView('notificationsBadge', 'views/notification/badge', {
el: this.options.el + ' .notifications-badge-container'
});
this.setupGlobalSearch();
this.setupTabDefsList();
this.once('remove', () => {
$(window).off('resize.navbar');
$(window).off('scroll.navbar');
$(window).off('scroll.navbar-tab-group');
});
},
filterTabItem: function (scope) {
@@ -890,6 +885,30 @@ define('views/site/navbar', 'view', function (Dep) {
},
setupTabDefsList: function () {
var tabList = this.getTabList();
this.tabList = tabList.filter(item => {
if (!item) {
return false;
}
if (typeof item === 'object') {
item.itemList = item.itemList || [];
item.itemList = item.itemList.filter(item => {
return this.filterTabItem(item);
});
if (!item.itemList.length) {
return false;
}
return true;
}
return this.filterTabItem(item);
});
var tabDefsList = [];
var colorsDisabled =