Merge pull request #3610 from Icinga/fix/window-id-cannot-be-used-to-differentiate-containers-3609

Fix window id cannot be used to differentiate containers
This commit is contained in:
Johannes Meyer 2019-04-17 11:38:48 +02:00 committed by GitHub
commit f72aa291bc
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 69 additions and 7 deletions

View File

@ -85,6 +85,7 @@ $innerLayoutScript = $this->layout()->innerLayout . '.phtml';
<script type="text/javascript" src="<?= $this->href($jsfile) ?>"></script>
<!--<![endif]-->
<script type="text/javascript">
window.name = '<?= $this->protectId('Icinga') ?>';
var icinga = new Icinga({
baseUrl: '<?= $this->baseUrl(); ?>'
});

View File

@ -107,7 +107,12 @@
// Ask for a new window id in case we don't already have one
if (this.icinga.ui.hasWindowId()) {
headers['X-Icinga-WindowId'] = this.icinga.ui.getWindowId();
var windowId = this.icinga.ui.getWindowId();
var containerId = this.icinga.ui.getUniqueContainerId($target);
if (containerId) {
windowId = windowId + '_' + containerId;
}
headers['X-Icinga-WindowId'] = windowId;
} else {
headers['X-Icinga-WindowId'] = 'undefined';
}

View File

@ -197,7 +197,8 @@
'data-icinga-title': $col.data('icingaTitle'),
'data-icinga-refresh': $col.data('icingaRefresh'),
'data-last-update': $col.data('lastUpdate'),
'data-icinga-module': $col.data('icingaModule')
'data-icinga-module': $col.data('icingaModule'),
'data-icinga-container-id': $col.data('icingaContainerId')
},
'class': $col.attr('class')
};
@ -207,6 +208,7 @@
$col.removeData('icingaRefresh');
$col.removeData('lastUpdate');
$col.removeData('icingaModule');
$col.removeData('icingaContainerId');
$col.removeAttr('class').attr('class', 'container');
return props;
},
@ -219,6 +221,7 @@
$col.data('icingaRefresh', backup['data']['data-icinga-refresh']);
$col.data('lastUpdate', backup['data']['data-last-update']);
$col.data('icingaModule', backup['data']['data-icinga-module']);
$col.data('icingaContainerId', backup['data']['data-icinga-container-id']);
},
triggerWindowResize: function () {
@ -703,21 +706,44 @@
this.fixControls();
},
getUniqueContainerId: function ($cont) {
if (typeof $cont === 'undefined' || !$cont.length) {
return null;
}
var containerId = $cont.data('icingaContainerId');
if (typeof containerId === 'undefined') {
/**
* Only generate an id if it's not for col1 or the menu (which are using the non-suffixed window id).
* This is based on the assumption that the server only knows about the menu and first column
* and therefore does not need to protect its ids. (As the menu is most likely part of the sidebar)
*/
if ($cont.attr('id') === 'menu' || $cont.attr('id') === 'col1') {
return null;
}
containerId = this.icinga.utils.generateId(6); // Random because the content may move
$cont.data('icingaContainerId', containerId);
}
return containerId;
},
getWindowId: function () {
if (! this.hasWindowId()) {
return undefined;
}
return window.name.match(/^Icinga_([a-zA-Z0-9]+)$/)[1];
return window.name.match(/^Icinga-([a-zA-Z0-9]+)$/)[1];
},
hasWindowId: function () {
var res = window.name.match(/^Icinga_([a-zA-Z0-9]+)$/);
var res = window.name.match(/^Icinga-([a-zA-Z0-9]+)$/);
return typeof res === 'object' && null !== res;
},
setWindowId: function (id) {
this.icinga.logger.debug('Setting new window id', id);
window.name = 'Icinga_' + id;
window.name = 'Icinga-' + id;
},
destroy: function () {

View File

@ -286,8 +286,7 @@
while (true) {
var id = $node.attr('id');
// Ignore forms and form controls because id generation is unreliable :(
if (typeof id !== 'undefined' && ! $node.is(':input') && ! $node.is('form')) {
if (typeof id !== 'undefined') {
path.push('#' + id);
break;
}
@ -412,6 +411,37 @@
str = padding + str;
}
return str;
},
/**
* Shuffle a string
*
* @param {String} str The string to shuffle
*
* @returns {String} The shuffled string
*/
shuffleString: function(str) {
var a = str.split(""),
n = a.length;
for(var i = n - 1; i > 0; i--) {
var j = Math.floor(Math.random() * (i + 1));
var tmp = a[i];
a[i] = a[j];
a[j] = tmp;
}
return a.join("");
},
/**
* Generate an id
*
* @param {Number} len The desired length of the id
*
* @returns {String} The id
*/
generateId: function(len) {
return this.shuffleString('abcefghijklmnopqrstuvwxyz').substr(0, len);
}
};