JS cleanup

* Precedence rules: skip autorefresh if click is pending
* Clean up the attr VS data mess
* More steps towards a column-count-ignorant GUI
This commit is contained in:
Thomas Gelf 2014-03-17 17:10:03 +01:00
parent 2febbdd7d5
commit e0c93d6ca7
4 changed files with 72 additions and 39 deletions

View File

@ -2,7 +2,7 @@
<?= $this->render('show/components/header.phtml') ?>
<h1>This service's current state</h1>
</div>
<div class="content" data-base-target="col1">
<div class="content" data-base-target="_next">
<?= $this->render('show/components/output.phtml') ?>
<table class="avp">

View File

@ -28,7 +28,7 @@
var icinga = this.icinga;
$('.dashboard > div', el).each(function(idx, el) {
var url = $(el).attr('data-icinga-url');
var url = $(el).data('icingaUrl');
if (typeof url === 'undefined') return;
icinga.loader.loadUrl(url, $(el)).autorefresh = true;
});
@ -37,13 +37,14 @@
$('table.action tr', el).each(function(idx, el) {
var $a = $('a[href]', el).first();
if ($a.length) {
// TODO: Find out whether we leak memory on IE with this:
$(el).attr('href', $a.attr('href'));
}
});
$('.icinga-module', el).each(function(idx, mod) {
var $mod = $(mod);
var moduleName = $mod.data('icinga-module');
var moduleName = $mod.data('icingaModule');
if (icinga.hasModule(moduleName)) {
var module = icinga.module(moduleName);
// NOT YET, the applyOnloadDings: module.applyEventHandlers(mod);
@ -134,7 +135,7 @@
// .closest is not required unless subelements to trigger this
var $form = $(event.currentTarget).closest('form');
var url = $form.attr('action');
var url = $form.attr('action').replace('&amp;', '&'); // WHY??
var method = $form.attr('method');
var $target;
var data = $form.serializeArray();
@ -244,6 +245,9 @@
// ...the only exception are class="action" tables...
if ($el.closest('table.action').length) {
if ($el.closest('#col2').length) {
this.icinga.ui.moveToLeft();
}
$target = $('#col2');
}
@ -253,6 +257,9 @@
// Simulate _next to prepare migration to dynamic column layout
if (targetId === '_next') {
if ($el.closest('#col2').length) {
this.icinga.ui.moveToLeft();
}
targetId = 'col2';
}

View File

@ -45,7 +45,7 @@
* @param {object} data Optional parameters, usually for POST requests
* @param {string} method HTTP method, default is 'GET'
*/
loadUrl: function (url, $target, data, method) {
loadUrl: function (url, $target, data, method, autorefresh = false) {
var id = null;
// Default method is GET
@ -60,18 +60,11 @@
id = $target.attr('id');
}
if (typeof $target !== 'undefined') {
// TODO: We shouldn't use data but keep this information somewhere else.
if ($target.data('icingaUrl') !== url) {
$target.removeAttr('data-icinga-url');
$target.removeAttr('data-icinga-refresh');
$target.removeData('icingaUrl');
$target.removeData('icingaRefresh');
}
}
// If we have a pending request for the same target...
if (id in this.requests) {
if (autorefresh) {
return false;
}
// ...ignore the new request if it is already pending with the same URL
if (this.requests[id].url === url) {
this.icinga.logger.debug('Request to ', url, ' is already running for ', $target);
@ -113,7 +106,7 @@
req.fail(this.onFailure);
req.complete(this.onComplete);
req.historyTriggered = false;
req.autorefresh = false;
req.autorefresh = autorefresh;
if (id) {
this.requests[id] = req;
}
@ -144,17 +137,21 @@
}
},
filterAutorefreshingContainers: function () {
return $(this).data('icingaRefresh') > 0;
},
autorefresh: function () {
var self = this;
if (self.autorefreshEnabled !== true) {
return;
}
$('.container[data-icinga-refresh]').each(function (idx, el) {
$('.container').filter(this.filterAutorefreshingContainers).each(function (idx, el) {
var $el = $(el);
var id = $el.attr('id');
if (id in self.requests) {
self.icinga.logger.debug('No refresh, request pending', id);
self.icinga.logger.debug('No refresh, request pending for ', id);
return;
}
@ -185,10 +182,15 @@
return;
}
self.icinga.logger.info(
'Autorefreshing ' + id + ' ' + interval + ' ms passed'
);
self.loadUrl($el.data('icingaUrl'), $el).autorefresh = true;
if (self.loadUrl($el.data('icingaUrl'), $el, undefined, undefined, true) === false) {
self.icinga.logger.debug(
'NOT autorefreshing ' + id + ', even if ' + interval + ' ms passed. Request pending?'
);
} else {
self.icinga.logger.debug(
'Autorefreshing ' + id + ' ' + interval + ' ms passed'
);
}
el = null;
});
},
@ -287,6 +289,17 @@
newBody = true;
}
var moduleName = req.getResponseHeader('X-Icinga-Module');
if (moduleName) {
req.$target.addClass('icinga-module');
req.$target.data('icingaModule', moduleName);
req.$target.addClass('module-' + moduleName);
} else {
req.$target.removeClass('icinga-module');
req.$target.removeData('icingaModule');
req.$target.attr('class', 'container'); // TODO: remove module-$name
}
var title = req.getResponseHeader('X-Icinga-Title');
if (title && req.$target.closest('.dashboard').length === 0) {
this.icinga.ui.setTitle(title);
@ -295,13 +308,9 @@
var refresh = req.getResponseHeader('X-Icinga-Refresh');
if (refresh) {
// Hmmmm... .data() doesn't work here?
req.$target.attr('data-icinga-refresh', refresh);
req.$target.attr('data-last-update', (new Date()).getTime());
req.$target.data('lastUpdate', (new Date()).getTime());
req.$target.data('icingaRefresh', refresh);
} else {
req.$target.removeAttr('data-icinga-refresh');
req.$target.removeAttr('data-last-update');
req.$target.removeData('icingaRefresh');
req.$target.removeData('lastUpdate');
}
@ -342,7 +351,6 @@
return;
}
req.$target.attr('data-icinga-url', req.url);
req.$target.data('icingaUrl', req.url);
// Update history when necessary. Don't do so for requests triggered

View File

@ -40,7 +40,7 @@
.fadeOut('slow',
function() {
icinga.ui.fixControls();
this.remove();
$(this).remove();
});
},
@ -91,17 +91,35 @@
return this;
},
flipContent: function () {
var col1 = $('#col1 > div').detach();
var col2 = $('#col2 > div').detach();
$('#col2').html('');
$('#col1').html('');
col1.appendTo('#col2');
col2.appendTo('#col1');
moveToLeft: function () {
var col2 = this.cutContainer($('#col2'));
var kill = this.cutContainer($('#col1'));
this.pasteContainer($('#col1'), col2);
this.fixControls();
},
cutContainer: function ($col) {
return {
'elements': $('#' + $col.attr('id') + ' > div').detach(),
'data': {
'data-icinga-url': $col.data('icingaUrl'),
'data-icinga-refresh': $col.data('icingaRefresh'),
'data-last-update': $col.data('lastUpdate'),
'data-icinga-module': $col.data('icingaModule')
},
'class': $col.attr('class')
}
},
pasteContainer: function ($col, backup) {
backup['elements'].appendTo($col);
$col.attr('class', backup['class']); // TODO: ie memleak? remove first?
$col.data('icingaUrl', backup['data']['data-icinga-url']);
$col.data('icingaRefresh', backup['data']['data-icinga-refresh']);
$col.data('lastUpdate', backup['data']['data-last-update']);
$col.data('icingaModule', backup['data']['data-icinga-module']);
},
triggerWindowResize: function () {
this.onWindowResize({data: {self: this}});
},
@ -136,7 +154,7 @@
$('#layout').removeClass(this.currentLayout + '-layout').addClass(layout);
this.currentLayout = matched[1];
if (this.currentLayout === 'poor' || this.currentLayout === 'minimal') {
this.icinga.events.layout1col();
this.layout1col();
}
return true;
}
@ -155,10 +173,10 @@
var $col2 = $('#col2');
icinga.logger.debug('Switching to single col');
$('#layout').removeClass('twocols');
$col2.removeAttr('data-icinga-url');
$col2.removeAttr('data-icinga-refresh');
$col2.removeData('icingaUrl');
$col2.removeData('icingaRefresh');
$col2.removeData('lastUpdate');
$col2.removeData('icingaModule');
this.icinga.loader.stopPendingRequestsFor($col2);
$col2.html('');
this.fixControls();