';
$dialog.find('div.monitorUse').toggle(
logVars.log_output === 'TABLE' && (logVars.slow_query_log === 'ON' || logVars.general_log === 'ON')
);
$dialog.find('div.ajaxContent').html(str);
$dialog.find('img.ajaxIcon').hide();
$dialog.find('a.set').on('click', function () {
var nameValue = $(this).attr('href').split('-');
loadLogVars({ varName: nameValue[0].substr(1), varValue: nameValue[1] });
$dialog.find('img.ajaxIcon').show();
});
}
);
};
loadLogVars();
return false;
});
$('input[name="chartType"]').on('change', function () {
$('#chartVariableSettings').toggle(this.checked && this.value === 'variable');
var title = $('input[name="chartTitle"]').val();
if (title === Messages.strChartTitle ||
title === $('label[for="' + $('input[name="chartTitle"]').data('lastRadio') + '"]').text()
) {
$('input[name="chartTitle"]')
.data('lastRadio', $(this).attr('id'))
.val($('label[for="' + $(this).attr('id') + '"]').text());
}
});
$('input[name="useDivisor"]').on('change', function () {
$('span.divisorInput').toggle(this.checked);
});
$('input[name="useUnit"]').on('change', function () {
$('span.unitInput').toggle(this.checked);
});
$('select[name="varChartList"]').on('change', function () {
if (this.selectedIndex !== 0) {
$('#variableInput').val(this.value);
}
});
$('a[href="#kibDivisor"]').on('click', function (event) {
event.preventDefault();
$('input[name="valueDivisor"]').val(1024);
$('input[name="valueUnit"]').val(Messages.strKiB);
$('span.unitInput').toggle(true);
$('input[name="useUnit"]').prop('checked', true);
return false;
});
$('a[href="#mibDivisor"]').on('click', function (event) {
event.preventDefault();
$('input[name="valueDivisor"]').val(1024 * 1024);
$('input[name="valueUnit"]').val(Messages.strMiB);
$('span.unitInput').toggle(true);
$('input[name="useUnit"]').prop('checked', true);
return false;
});
$('a[href="#submitClearSeries"]').on('click', function (event) {
event.preventDefault();
$('#seriesPreview').html('' + Messages.strNone + '');
newChart = null;
$('#clearSeriesLink').hide();
});
$('a[href="#submitAddSeries"]').on('click', function (event) {
event.preventDefault();
if ($('#variableInput').val() === '') {
return false;
}
if (newChart === null) {
$('#seriesPreview').html('');
newChart = {
title: $('input[name="chartTitle"]').val(),
nodes: [],
series: [],
maxYLabel: 0
};
}
var serie = {
dataPoints: [{ type: 'statusvar', name: $('#variableInput').val() }],
display: $('input[name="differentialValue"]').prop('checked') ? 'differential' : ''
};
if (serie.dataPoints[0].name === 'Processes') {
serie.dataPoints[0].type = 'proc';
}
if ($('input[name="useDivisor"]').prop('checked')) {
serie.valueDivisor = parseInt($('input[name="valueDivisor"]').val(), 10);
}
if ($('input[name="useUnit"]').prop('checked')) {
serie.unit = $('input[name="valueUnit"]').val();
}
var str = serie.display === 'differential' ? ', ' + Messages.strDifferential : '';
str += serie.valueDivisor ? (', ' + Functions.sprintf(Messages.strDividedBy, serie.valueDivisor)) : '';
str += serie.unit ? (', ' + Messages.strUnit + ': ' + serie.unit) : '';
var newSeries = {
label: $('#variableInput').val().replace(/_/g, ' ')
};
newChart.series.push(newSeries);
$('#seriesPreview').append('- ' + Functions.escapeHtml(newSeries.label + str) + ' ');
newChart.nodes.push(serie);
$('#variableInput').val('');
$('input[name="differentialValue"]').prop('checked', true);
$('input[name="useDivisor"]').prop('checked', false);
$('input[name="useUnit"]').prop('checked', false);
$('input[name="useDivisor"]').trigger('change');
$('input[name="useUnit"]').trigger('change');
$('select[name="varChartList"]').get(0).selectedIndex = 0;
$('#clearSeriesLink').show();
return false;
});
$('#variableInput').autocomplete({
source: variableNames
});
/* Initializes the monitor, called only once */
function initGrid () {
var i;
/* Apply default values & config */
if (isStorageSupported('localStorage')) {
if (typeof window.localStorage.monitorCharts !== 'undefined') {
runtime.charts = JSON.parse(window.localStorage.monitorCharts);
}
if (typeof window.localStorage.monitorSettings !== 'undefined') {
monitorSettings = JSON.parse(window.localStorage.monitorSettings);
}
$('a[href="#clearMonitorConfig"]').toggle(runtime.charts !== null);
if (runtime.charts !== null
&& typeof window.localStorage.monitorVersion !== 'undefined'
&& monitorProtocolVersion !== window.localStorage.monitorVersion
) {
$('#emptyDialog').dialog({ title: Messages.strIncompatibleMonitorConfig });
$('#emptyDialog').html(Messages.strIncompatibleMonitorConfigDescription);
var dlgBtns = {};
dlgBtns[Messages.strClose] = function () {
$(this).dialog('close');
};
$('#emptyDialog').dialog({
width: 400,
buttons: dlgBtns
});
}
}
if (runtime.charts === null) {
runtime.charts = defaultChartGrid;
}
if (monitorSettings === null) {
monitorSettings = defaultMonitorSettings;
}
$('select[name="gridChartRefresh"]').val(monitorSettings.gridRefresh / 1000);
$('select[name="chartColumns"]').val(monitorSettings.columns);
if (monitorSettings.gridMaxPoints === 'auto') {
runtime.gridMaxPoints = Math.round((monitorSettings.chartSize.width - 40) / 12);
} else {
runtime.gridMaxPoints = monitorSettings.gridMaxPoints;
}
runtime.xmin = new Date().getTime() - serverTimeDiff - runtime.gridMaxPoints * monitorSettings.gridRefresh;
runtime.xmax = new Date().getTime() - serverTimeDiff + monitorSettings.gridRefresh;
/* Calculate how much spacing there is between each chart */
$('#chartGrid').html('
');
chartSpacing = {
width: $('#chartGrid').find('td').eq(1).offset().left -
$('#chartGrid').find('td').eq(0).offset().left,
height: $('#chartGrid').find('tr').eq(1).find('td').eq(1).offset().top -
$('#chartGrid').find('tr').eq(0).find('td').eq(0).offset().top
};
$('#chartGrid').html('');
/* Add all charts - in correct order */
var keys = [];
$.each(runtime.charts, function (key) {
keys.push(key);
});
keys.sort();
for (i = 0; i < keys.length; i++) {
addChart(runtime.charts[keys[i]], true);
}
/* Fill in missing cells */
var numCharts = $('#chartGrid').find('.monitorChart').length;
var numMissingCells = (monitorSettings.columns - numCharts % monitorSettings.columns) % monitorSettings.columns;
for (i = 0; i < numMissingCells; i++) {
$('#chartGrid').find('tr').last().append('
');
}
// Empty cells should keep their size so you can drop onto them
calculateChartSize();
$('#chartGrid').find('tr td').css('width', chartSize.width + 'px');
buildRequiredDataList();
refreshChartGrid();
}
/* Calls destroyGrid() and initGrid(), but before doing so it saves the chart
* data from each chart and restores it after the monitor is initialized again */
function rebuildGrid () {
var oldData = null;
if (runtime.charts) {
oldData = {};
$.each(runtime.charts, function (key, chartObj) {
for (var i = 0, l = chartObj.nodes.length; i < l; i++) {
oldData[chartObj.nodes[i].dataPoint] = [];
for (var j = 0, ll = chartObj.chart.series[i].data.length; j < ll; j++) {
oldData[chartObj.nodes[i].dataPoint].push([chartObj.chart.series[i].data[j].x, chartObj.chart.series[i].data[j].y]);
}
}
});
}
destroyGrid();
initGrid();
}
/* Calculates the dynamic chart size that depends on the column width */
function calculateChartSize () {
var panelWidth;
if ($('body').height() > $(window).height()) { // has vertical scroll bar
panelWidth = $('#logTable').innerWidth();
} else {
panelWidth = $('#logTable').innerWidth() - 10; // leave some space for vertical scroll bar
}
var wdt = panelWidth;
var windowWidth = $(window).width();
if (windowWidth > 768) {
wdt = (panelWidth - monitorSettings.columns * chartSpacing.width) / monitorSettings.columns;
}
chartSize = {
width: Math.floor(wdt),
height: Math.floor(0.75 * wdt)
};
}
/* Adds a chart to the chart grid */
function addChart (chartObj, initialize) {
var i;
var settings = {
title: Functions.escapeHtml(chartObj.title),
grid: {
drawBorder: false,
shadow: false,
background: 'rgba(0,0,0,0)'
},
axes: {
xaxis: {
renderer: $.jqplot.DateAxisRenderer,
tickOptions: {
formatString: '%H:%M:%S',
showGridline: false
},
min: runtime.xmin,
max: runtime.xmax
},
yaxis: {
min: 0,
max: 100,
tickInterval: 20
}
},
seriesDefaults: {
rendererOptions: {
smooth: true
},
showLine: true,
lineWidth: 2,
markerOptions: {
size: 6
}
},
highlighter: {
show: true
}
};
if (settings.title === Messages.strSystemCPUUsage ||
settings.title === Messages.strQueryCacheEfficiency
) {
settings.axes.yaxis.tickOptions = {
formatString: '%d %%'
};
} else if (settings.title === Messages.strSystemMemory ||
settings.title === Messages.strSystemSwap
) {
settings.stackSeries = true;
settings.axes.yaxis.tickOptions = {
formatter: $.jqplot.byteFormatter(2) // MiB
};
} else if (settings.title === Messages.strTraffic) {
settings.axes.yaxis.tickOptions = {
formatter: $.jqplot.byteFormatter(1) // KiB
};
} else if (settings.title === Messages.strQuestions ||
settings.title === Messages.strConnections
) {
settings.axes.yaxis.tickOptions = {
formatter: function (format, val) {
if (Math.abs(val) >= 1000000) {
return $.jqplot.sprintf('%.3g M', val / 1000000);
} else if (Math.abs(val) >= 1000) {
return $.jqplot.sprintf('%.3g k', val / 1000);
} else {
return $.jqplot.sprintf('%d', val);
}
}
};
}
settings.series = chartObj.series;
if ($('#' + 'gridchart' + runtime.chartAI).length === 0) {
var numCharts = $('#chartGrid').find('.monitorChart').length;
if (numCharts === 0 || (numCharts % monitorSettings.columns === 0)) {
$('#chartGrid').append('
');
}
if (!chartSize) {
calculateChartSize();
}
$('#chartGrid').find('tr').last().append(
'
' +
'' +
'
'
);
}
// Set series' data as [0,0], smooth lines won't plot with data array having null values.
// also chart won't plot initially with no data and data comes on refreshChartGrid()
var series = [];
for (i in chartObj.series) {
series.push([[0, 0]]);
}
var tempTooltipContentEditor = function (str, seriesIndex, pointIndex, plot) {
var j;
// TODO: move style to theme CSS
var tooltipHtml = '
';
// x value i.e. time
var timeValue = str.split(',')[0];
var seriesValue;
tooltipHtml += 'Time: ' + timeValue;
tooltipHtml += '';
// Add y values to the tooltip per series
for (j in plot.series) {
// get y value if present
if (plot.series[j].data.length > pointIndex) {
seriesValue = plot.series[j].data[pointIndex][1];
} else {
return;
}
var seriesLabel = plot.series[j].label;
var seriesColor = plot.series[j].color;
// format y value
if (plot.series[0]._yaxis.tickOptions.formatter) { // eslint-disable-line no-underscore-dangle
// using formatter function
// eslint-disable-next-line no-underscore-dangle
seriesValue = plot.series[0]._yaxis.tickOptions.formatter('%s', seriesValue);
} else if (plot.series[0]._yaxis.tickOptions.formatString) { // eslint-disable-line no-underscore-dangle
// using format string
// eslint-disable-next-line no-underscore-dangle
seriesValue = Functions.sprintf(plot.series[0]._yaxis.tickOptions.formatString, seriesValue);
}
tooltipHtml += ' ' +
seriesLabel + ': ' + seriesValue + '';
}
tooltipHtml += '
';
return tooltipHtml;
};
// set Tooltip for each series
for (i in settings.series) {
settings.series[i].highlighter = {
show: true,
tooltipContentEditor: tempTooltipContentEditor
};
}
chartObj.chart = $.jqplot('gridchart' + runtime.chartAI, series, settings);
// remove [0,0] after plotting
for (i in chartObj.chart.series) {
chartObj.chart.series[i].data.shift();
}
var $legend = $('').css('padding', '0.5em');
for (i in chartObj.chart.series) {
$legend.append(
$('').append(
$('
')
).addClass('floatleft')
);
}
$('#gridchart' + runtime.chartAI)
.parent()
.append($legend);
if (initialize !== true) {
runtime.charts['c' + runtime.chartAI] = chartObj;
buildRequiredDataList();
}
// time span selection
$('#gridchart' + runtime.chartAI).on('jqplotMouseDown', function (ev, gridpos, datapos) {
drawTimeSpan = true;
selectionTimeDiff.push(datapos.xaxis);
if ($('#selection_box').length) {
$('#selection_box').remove();
}
var selectionBox = $('
');
$(document.body).append(selectionBox);
selectionStartX = ev.pageX;
selectionStartY = ev.pageY;
selectionBox
.attr({ id: 'selection_box' })
.css({
top: selectionStartY - gridpos.y,
left: selectionStartX
})
.fadeIn();
});
$('#gridchart' + runtime.chartAI).on('jqplotMouseUp', function (ev, gridpos, datapos) {
if (! drawTimeSpan || editMode) {
return;
}
selectionTimeDiff.push(datapos.xaxis);
if (selectionTimeDiff[1] <= selectionTimeDiff[0]) {
selectionTimeDiff = [];
return;
}
// get date from timestamp
var min = new Date(Math.ceil(selectionTimeDiff[0]));
var max = new Date(Math.ceil(selectionTimeDiff[1]));
getLogAnalyseDialog(min, max);
selectionTimeDiff = [];
drawTimeSpan = false;
});
$('#gridchart' + runtime.chartAI).on('jqplotMouseMove', function (ev) {
if (! drawTimeSpan || editMode) {
return;
}
if (selectionStartX !== undefined) {
$('#selection_box')
.css({
width: Math.ceil(ev.pageX - selectionStartX)
})
.fadeIn();
}
});
$('#gridchart' + runtime.chartAI).on('jqplotMouseLeave', function () {
drawTimeSpan = false;
});
$(document.body).on('mouseup', function () {
if ($('#selection_box').length) {
$('#selection_box').remove();
}
});
// Edit, Print icon only in edit mode
$('#chartGrid').find('div svg').find('*[zIndex=20], *[zIndex=21], *[zIndex=19]').toggle(editMode);
runtime.chartAI++;
}
function getLogAnalyseDialog (min, max) {
var $logAnalyseDialog = $('#logAnalyseDialog');
var $dateStart = $logAnalyseDialog.find('input[name="dateStart"]');
var $dateEnd = $logAnalyseDialog.find('input[name="dateEnd"]');
$dateStart.prop('readonly', true);
$dateEnd.prop('readonly', true);
var dlgBtns = { };
dlgBtns[Messages.strFromSlowLog] = function () {
loadLog('slow', min, max);
$(this).dialog('close');
};
dlgBtns[Messages.strFromGeneralLog] = function () {
loadLog('general', min, max);
$(this).dialog('close');
};
$logAnalyseDialog.dialog({
width: 'auto',
height: 'auto',
buttons: dlgBtns
});
Functions.addDatepicker($dateStart, 'datetime', {
showMillisec: false,
showMicrosec: false,
timeFormat: 'HH:mm:ss',
firstDay: firstDayOfCalendar
});
Functions.addDatepicker($dateEnd, 'datetime', {
showMillisec: false,
showMicrosec: false,
timeFormat: 'HH:mm:ss',
firstDay: firstDayOfCalendar
});
$dateStart.datepicker('setDate', min);
$dateEnd.datepicker('setDate', max);
}
function loadLog (type, min, max) {
var dateStart = Date.parse($('#logAnalyseDialog').find('input[name="dateStart"]').datepicker('getDate')) || min;
var dateEnd = Date.parse($('#logAnalyseDialog').find('input[name="dateEnd"]').datepicker('getDate')) || max;
loadLogStatistics({
src: type,
start: dateStart,
end: dateEnd,
removeVariables: $('#removeVariables').prop('checked'),
limitTypes: $('#limitTypes').prop('checked')
});
}
/* Called in regular intervals, this function updates the values of each chart in the grid */
function refreshChartGrid () {
/* Send to server */
runtime.refreshRequest = $.post('index.php?route=/server/status/monitor/chart', {
'ajax_request': true,
'requiredData': JSON.stringify(runtime.dataList),
'server': CommonParams.get('server')
}, function (data) {
var chartData;
if (typeof data !== 'undefined' && data.success === true) {
chartData = data.message;
} else {
return serverResponseError();
}
var value;
var i = 0;
var diff;
var total;
/* Update values in each graph */
$.each(runtime.charts, function (orderKey, elem) {
var key = elem.chartID;
// If newly added chart, we have no data for it yet
if (! chartData[key]) {
return;
}
// Draw all series
total = 0;
for (var j = 0; j < elem.nodes.length; j++) {
// Update x-axis
if (i === 0 && j === 0) {
if (oldChartData === null) {
diff = chartData.x - runtime.xmax;
} else {
diff = parseInt(chartData.x - oldChartData.x, 10);
}
runtime.xmin += diff;
runtime.xmax += diff;
}
// elem.chart.xAxis[0].setExtremes(runtime.xmin, runtime.xmax, false);
/* Calculate y value */
// If transform function given, use it
if (elem.nodes[j].transformFn) {
value = chartValueTransform(
elem.nodes[j].transformFn,
chartData[key][j],
// Check if first iteration (oldChartData==null), or if newly added chart oldChartData[key]==null
(
oldChartData === null ||
oldChartData[key] === null ||
oldChartData[key] === undefined ? null : oldChartData[key][j]
)
);
// Otherwise use original value and apply differential and divisor if given,
// in this case we have only one data point per series - located at chartData[key][j][0]
} else {
value = parseFloat(chartData[key][j][0].value);
if (elem.nodes[j].display === 'differential') {
if (oldChartData === null ||
oldChartData[key] === null ||
oldChartData[key] === undefined
) {
continue;
}
value -= oldChartData[key][j][0].value;
}
if (elem.nodes[j].valueDivisor) {
value = value / elem.nodes[j].valueDivisor;
}
}
// Set y value, if defined
if (value !== undefined) {
elem.chart.series[j].data.push([chartData.x, value]);
if (value > elem.maxYLabel) {
elem.maxYLabel = value;
} else if (elem.maxYLabel === 0) {
elem.maxYLabel = 0.5;
}
// free old data point values and update maxYLabel
if (elem.chart.series[j].data.length > runtime.gridMaxPoints &&
elem.chart.series[j].data[0][0] < runtime.xmin
) {
// check if the next freeable point is highest
if (elem.maxYLabel <= elem.chart.series[j].data[0][1]) {
elem.chart.series[j].data.splice(0, elem.chart.series[j].data.length - runtime.gridMaxPoints);
elem.maxYLabel = getMaxYLabel(elem.chart.series[j].data);
} else {
elem.chart.series[j].data.splice(0, elem.chart.series[j].data.length - runtime.gridMaxPoints);
}
}
if (elem.title === Messages.strSystemMemory ||
elem.title === Messages.strSystemSwap
) {
total += value;
}
}
}
// update chart options
// keep ticks number/positioning consistent while refreshrate changes
var tickInterval = (runtime.xmax - runtime.xmin) / 5;
elem.chart.axes.xaxis.ticks = [(runtime.xmax - tickInterval * 4),
(runtime.xmax - tickInterval * 3), (runtime.xmax - tickInterval * 2),
(runtime.xmax - tickInterval), runtime.xmax];
if (elem.title !== Messages.strSystemCPUUsage &&
elem.title !== Messages.strQueryCacheEfficiency &&
elem.title !== Messages.strSystemMemory &&
elem.title !== Messages.strSystemSwap
) {
elem.chart.axes.yaxis.max = Math.ceil(elem.maxYLabel * 1.1);
elem.chart.axes.yaxis.tickInterval = Math.ceil(elem.maxYLabel * 1.1 / 5);
} else if (elem.title === Messages.strSystemMemory ||
elem.title === Messages.strSystemSwap
) {
elem.chart.axes.yaxis.max = Math.ceil(total * 1.1 / 100) * 100;
elem.chart.axes.yaxis.tickInterval = Math.ceil(total * 1.1 / 5);
}
i++;
if (runtime.redrawCharts) {
elem.chart.replot();
}
});
oldChartData = chartData;
runtime.refreshTimeout = setTimeout(refreshChartGrid, monitorSettings.gridRefresh);
});
}
/* Function to get highest plotted point's y label, to scale the chart,
* TODO: make jqplot's autoscale:true work here
*/
function getMaxYLabel (dataValues) {
var maxY = dataValues[0][1];
$.each(dataValues, function (k, v) {
maxY = (v[1] > maxY) ? v[1] : maxY;
});
return maxY;
}
/* Function that supplies special value transform functions for chart values */
function chartValueTransform (name, cur, prev) {
switch (name) {
case 'cpu-linux':
if (prev === null) {
return undefined;
}
// cur and prev are datapoint arrays, but containing
// only 1 element for cpu-linux
var newCur = cur[0];
var newPrev = prev[0];
var diffTotal = newCur.busy + newCur.idle - (newPrev.busy + newPrev.idle);
var diffIdle = newCur.idle - newPrev.idle;
return 100 * (diffTotal - diffIdle) / diffTotal;
// Query cache efficiency (%)
case 'qce':
if (prev === null) {
return undefined;
}
// cur[0].value is Qcache_hits, cur[1].value is Com_select
var diffQHits = cur[0].value - prev[0].value;
// No NaN please :-)
if (cur[1].value - prev[1].value === 0) {
return 0;
}
return diffQHits / (cur[1].value - prev[1].value + diffQHits) * 100;
// Query cache usage (%)
case 'qcu':
if (cur[1].value === 0) {
return 0;
}
// cur[0].value is Qcache_free_memory, cur[1].value is query_cache_size
return 100 - cur[0].value / cur[1].value * 100;
}
return undefined;
}
/* Build list of nodes that need to be retrieved from server.
* It creates something like a stripped down version of the runtime.charts object.
*/
function buildRequiredDataList () {
runtime.dataList = {};
// Store an own id, because the property name is subject of reordering,
// thus destroying our mapping with runtime.charts <=> runtime.dataList
var chartID = 0;
$.each(runtime.charts, function (key, chart) {
runtime.dataList[chartID] = [];
for (var i = 0, l = chart.nodes.length; i < l; i++) {
runtime.dataList[chartID][i] = chart.nodes[i].dataPoints;
}
runtime.charts[key].chartID = chartID;
chartID++;
});
}
/* Loads the log table data, generates the table and handles the filters */
function loadLogStatistics (opts) {
var logRequest = null;
if (! opts.removeVariables) {
opts.removeVariables = false;
}
if (! opts.limitTypes) {
opts.limitTypes = false;
}
$('#emptyDialog').dialog({ title: Messages.strAnalysingLogsTitle });
$('#emptyDialog').html(Messages.strAnalysingLogs +
' ');
var dlgBtns = {};
dlgBtns[Messages.strCancelRequest] = function () {
if (logRequest !== null) {
logRequest.abort();
}
$(this).dialog('close');
};
$('#emptyDialog').dialog({
width: 'auto',
height: 'auto',
buttons: dlgBtns
});
var url = 'index.php?route=/server/status/monitor/slow-log';
if (opts.src === 'general') {
url = 'index.php?route=/server/status/monitor/general-log';
}
logRequest = $.post(
url,
{
'ajax_request': true,
'time_start': Math.round(opts.start / 1000),
'time_end': Math.round(opts.end / 1000),
'removeVariables': opts.removeVariables,
'limitTypes': opts.limitTypes,
'server': CommonParams.get('server')
},
function (data) {
var logData;
var dlgBtns = {};
if (typeof data !== 'undefined' && data.success === true) {
logData = data.message;
} else {
return serverResponseError();
}
if (logData.rows.length === 0) {
$('#emptyDialog').dialog({ title: Messages.strNoDataFoundTitle });
$('#emptyDialog').html('
' + Messages.strNoDataFound + '
');
dlgBtns[Messages.strClose] = function () {
$(this).dialog('close');
};
$('#emptyDialog').dialog('option', 'buttons', dlgBtns);
return;
}
runtime.logDataCols = buildLogTable(logData, opts.removeVariables);
/* Show some stats in the dialog */
$('#emptyDialog').dialog({ title: Messages.strLoadingLogs });
$('#emptyDialog').html('
' + Messages.strLogDataLoaded + '
');
$.each(logData.sum, function (key, value) {
var newKey = key.charAt(0).toUpperCase() + key.slice(1).toLowerCase();
if (newKey === 'Total') {
newKey = '' + newKey + '';
}
$('#emptyDialog').append(newKey + ': ' + value + ' ');
});
/* Add filter options if more than a bunch of rows there to filter */
if (logData.numRows > 12) {
$('#logTable').prepend(
'