feature: Added support for populating selects from ajax (#6557)

fixes: #5264

The issue was all the string concatenation...

But I decided to try loading the select via ajax. Seems ok.  We could just use something like select2.  Opinions? Use this approach or load at page load.
I was able to reduce the loading of the 4000 select items from 1.6s to 0.6s on my laptop by optimizing the sql.

I added 4000 devices to my database to check this :)
This commit is contained in:
Tony Murray
2017-05-03 16:51:01 -05:00
committed by Neil Lathwood
parent 02d9b36720
commit 2b3ca49bea
5 changed files with 123 additions and 43 deletions

33
html/ajax_list.php Normal file
View File

@ -0,0 +1,33 @@
<?php
/*
* LibreNMS
*
* Copyright (c) 2014 Neil Lathwood <https://github.com/laf/ http://www.lathwood.co.uk/fa>
* Copyright (c) 2017 Tony Murray <https://github.com/murrant/>
*
* This program 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. Please see LICENSE.txt at the top level of
* the source code distribution for details.
*/
$init_modules = array('web', 'auth');
require realpath(__DIR__ . '/..') . '/includes/init.php';
if (!$_SESSION['authenticated']) {
echo "Unauthenticated\n";
exit;
}
set_debug($_REQUEST['debug']);
$id = mres($_REQUEST['id']);
if (isset($id)) {
if (file_exists("includes/list/$id.inc.php")) {
header('Content-type: application/json');
include_once "includes/list/$id.inc.php";
}
}

View File

@ -22,18 +22,18 @@ if (!$_SESSION['authenticated']) {
set_debug($_REQUEST['debug']); set_debug($_REQUEST['debug']);
$current = $_POST['current']; $current = $_REQUEST['current'];
settype($current, 'integer'); settype($current, 'integer');
$rowCount = $_POST['rowCount']; $rowCount = $_REQUEST['rowCount'];
settype($rowCount, 'integer'); settype($rowCount, 'integer');
if (isset($_POST['sort']) && is_array($_POST['sort'])) { if (isset($_REQUEST['sort']) && is_array($_POST['sort'])) {
foreach ($_POST['sort'] as $k => $v) { foreach ($_REQUEST['sort'] as $k => $v) {
$sort .= " $k $v"; $sort .= " $k $v";
} }
} }
$searchPhrase = mres($_POST['searchPhrase']); $searchPhrase = mres($_REQUEST['searchPhrase']);
$id = mres($_POST['id']); $id = mres($_REQUEST['id']);
$response = array(); $response = array();
if (isset($id)) { if (isset($id)) {

View File

@ -1604,3 +1604,27 @@ function get_dashboards($user_id = null)
return $result; return $result;
} }
/**
* Generate javascript to fill in a select box from an ajax list
*
* @param string $list_type type of list look in html/includes/list/
* @param string $selector jquery selector for the target select element
* @param int $selected the id of the item to mark as selected
* @return string the javascript (not including <script> tags)
*/
function generate_fill_select_js($list_type, $selector, $selected = null)
{
return '$(document).ready(function() {
$select = $("' . $selector . '")
$.getJSON(\'ajax_list.php?id=' . $list_type . '\', function(data){
$.each(data, function(index,item) {
if (item.id == "' . $selected . '") {
$select.append("<option value=" + item.id + " selected>" + item.value + "</option>");
} else {
$select.append("<option value=" + item.id + ">" + item.value + "</option>");
}
});
});
});';
}

View File

@ -0,0 +1,34 @@
<?php
/**
* hostnames.inc.php
*
* -Description-
*
* This program 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.
*
* This program 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 this program. If not, see <http://www.gnu.org/licenses/>.
*
* @package LibreNMS
* @link http://librenms.org
* @copyright 2017 Tony Murray
* @author Tony Murray <murraytony@gmail.com>
*/
if (is_admin() || is_read()) {
echo json_encode(dbFetchRows('SELECT `device_id` AS id, `hostname` AS value FROM `devices`'));
} else {
$sql = 'SELECT `devices`.`device_id` AS id, `hostname` AS value FROM `devices`
LEFT JOIN `devices_perms` ON `devices`.`device_id` = `devices_perms`.`device_id`
WHERE `devices_perms`.`user_id` = ?';
echo json_encode(dbFetchRows($sql, $_SESSION['user_id']));
}

View File

@ -37,43 +37,30 @@ $pagetitle[] = 'Alert Log';
var grid = $("#alertlog").bootgrid({ var grid = $("#alertlog").bootgrid({
ajax: true, ajax: true,
templates: { templates: {
header: "<div id=\"{{ctx.id}}\" class=\"{{css.header}}\"><div class=\"row\">"+ header: '<div id="{{ctx.id}}" class="{{css.header}}"><div class="row"> \
"<div class=\"col-sm-8 actionBar\"><span class=\"pull-left\">"+ <div class="col-sm-8 actionBar"><span class="pull-left"> \
"<form method=\"post\" action=\"\" class=\"form-inline\" role=\"form\" id=\"result_form\">"+ <form method="post" action="" class="form-inline" role="form" id="result_form"> \
"<div class=\"form-group\">"+ <div class="form-group"> \
"<label>"+ <label> \
"<strong>Device&nbsp;</strong>"+ <strong>Device&nbsp;</strong> \
"</label>"+ </label> \
"<select name=\"device_id\" id=\"device_id\" class=\"form-control input-sm\">"+ <select name="device_id" id="device_id" class="form-control input-sm" style="min-width: 175px;"> \
"<option value=\"\">All Devices</option>"+ <option value="">All Devices</option> \
<?php </select> \
foreach (get_all_devices() as $hostname) { </div> \
$device_id = getidbyname($hostname); <div class="form-group"> \
if (device_permitted($device_id)) { <label> \
echo '"<option value=\"'.$device_id.'\""+'; <strong>&nbsp;State&nbsp;</strong> \
if (getidbyname($hostname) == $_POST['device_id']) { </label> \
echo '" selected "+'; <select name="state" id="state" class="form-control input-sm"> \
} <option value="-1"></option> \
<option value="0">Ok</option> \
echo '">'.$hostname.'</option>"+'; <option value="1">Alert</option> \
} </select> \
} </div> \
?> <button type="submit" class="btn btn-default input-sm">Filter</button> \
"</select>"+ </form></span></div> \
"</div>"+ <div class="col-sm-4 actionBar"><p class="{{css.search}}"></p><p class="{{css.actions}}"></p></div></div></div>'
"<div class=\"form-group\">"+
"<label>"+
"<strong>&nbsp;State&nbsp;</strong>"+
"</label>"+
"<select name=\"state\" id=\"state\" class=\"form-control input-sm\">"+
"<option value=\"-1\"></option>"+
"<option value=\"0\">Ok</option>"+
"<option value=\"1\">Alert</option>"+
"</select>"+
"</div>"+
"<button type=\"submit\" class=\"btn btn-default input-sm\">Filter</button>"+
"</form></span></div>"+
"<div class=\"col-sm-4 actionBar\"><p class=\"{{css.search}}\"></p><p class=\"{{css.actions}}\"></p></div></div></div>"
}, },
post: function () post: function ()
{ {
@ -116,4 +103,6 @@ foreach (get_all_devices() as $hostname) {
}); });
}); });
}); });
<?php echo generate_fill_select_js('hostnames', '#device_id', $_POST['device_id']); ?>
</script> </script>