luci-mod-network: reimplement diagnostics page as client side view
Signed-off-by: Jo-Philipp Wich <jo@mein.io>
This commit is contained in:
parent
870a406120
commit
ab07b8c4d9
5 changed files with 149 additions and 207 deletions
|
@ -38,7 +38,16 @@
|
||||||
"/proc/sys/kernel/hostname": [ "read" ],
|
"/proc/sys/kernel/hostname": [ "read" ],
|
||||||
"/proc/sys/net/netfilter/nf_conntrack_*": [ "read" ],
|
"/proc/sys/net/netfilter/nf_conntrack_*": [ "read" ],
|
||||||
"/proc/mounts": [ "read" ],
|
"/proc/mounts": [ "read" ],
|
||||||
"/usr/lib/lua/luci/version.lua": [ "read" ]
|
"/usr/lib/lua/luci/version.lua": [ "read" ],
|
||||||
|
"/bin/ping *": [ "exec" ],
|
||||||
|
"/bin/ping6 *": [ "exec" ],
|
||||||
|
"/bin/traceroute *": [ "exec" ],
|
||||||
|
"/bin/traceroute6 *": [ "exec" ],
|
||||||
|
"/usr/bin/ping *": [ "exec" ],
|
||||||
|
"/usr/bin/ping6 *": [ "exec" ],
|
||||||
|
"/usr/bin/traceroute *": [ "exec" ],
|
||||||
|
"/usr/bin/traceroute6 *": [ "exec" ],
|
||||||
|
"/usr/bin/nslookup *": [ "exec" ]
|
||||||
},
|
},
|
||||||
"ubus": {
|
"ubus": {
|
||||||
"file": [ "list", "read", "stat" ],
|
"file": [ "list", "read", "stat" ],
|
||||||
|
|
|
@ -0,0 +1,137 @@
|
||||||
|
'use strict';
|
||||||
|
'require fs';
|
||||||
|
'require ui';
|
||||||
|
'require uci';
|
||||||
|
|
||||||
|
return L.view.extend({
|
||||||
|
handleCommand: function(exec, args) {
|
||||||
|
var buttons = document.querySelectorAll('.diag-action > .cbi-button');
|
||||||
|
|
||||||
|
for (var i = 0; i < buttons.length; i++)
|
||||||
|
buttons[i].setAttribute('disabled', 'true');
|
||||||
|
|
||||||
|
return fs.exec(exec, args).then(function(res) {
|
||||||
|
var out = document.querySelector('.command-output');
|
||||||
|
out.style.display = '';
|
||||||
|
|
||||||
|
L.dom.content(out, [ res.stdout || '', res.stderr || '' ]);
|
||||||
|
}).catch(function(err) {
|
||||||
|
ui.addNotification(null, E('p', [ err ]))
|
||||||
|
}).finally(function() {
|
||||||
|
for (var i = 0; i < buttons.length; i++)
|
||||||
|
buttons[i].removeAttribute('disabled');
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
handlePing: function(ev, cmd) {
|
||||||
|
var exec = cmd || 'ping',
|
||||||
|
addr = ev.currentTarget.parentNode.previousSibling.value,
|
||||||
|
args = (exec == 'ping') ? [ '-c', '5', '-W', '1', addr ] : [ '-c', '5', addr ];
|
||||||
|
|
||||||
|
return this.handleCommand(exec, args);
|
||||||
|
},
|
||||||
|
|
||||||
|
handleTraceroute: function(ev, cmd) {
|
||||||
|
var exec = cmd || 'traceroute',
|
||||||
|
addr = ev.currentTarget.parentNode.previousSibling.value,
|
||||||
|
args = (exec == 'traceroute') ? [ '-q', '1', '-w', '1', '-n', addr ] : [ '-q', '1', '-w', '2', '-n', addr ];
|
||||||
|
|
||||||
|
return this.handleCommand(exec, args);
|
||||||
|
},
|
||||||
|
|
||||||
|
handleNslookup: function(ev, cmd) {
|
||||||
|
var addr = ev.currentTarget.parentNode.previousSibling.value;
|
||||||
|
|
||||||
|
return this.handleCommand('nslookup', [ addr ]);
|
||||||
|
},
|
||||||
|
|
||||||
|
load: function() {
|
||||||
|
return Promise.all([
|
||||||
|
L.resolveDefault(fs.stat('/bin/ping6'), {}),
|
||||||
|
L.resolveDefault(fs.stat('/usr/bin/ping6'), {}),
|
||||||
|
L.resolveDefault(fs.stat('/bin/traceroute6'), {}),
|
||||||
|
L.resolveDefault(fs.stat('/usr/bin/traceroute6'), {}),
|
||||||
|
uci.load('luci')
|
||||||
|
]);
|
||||||
|
},
|
||||||
|
|
||||||
|
render: function(res) {
|
||||||
|
var has_ping6 = res[0].path || res[1].path,
|
||||||
|
has_traceroute6 = res[2].path || res[3].path,
|
||||||
|
dns_host = uci.get('luci', 'diag', 'dns') || 'openwrt.org',
|
||||||
|
ping_host = uci.get('luci', 'diag', 'ping') || 'openwrt.org',
|
||||||
|
route_host = uci.get('luci', 'diag', 'route') || 'openwrt.org';
|
||||||
|
|
||||||
|
return E([], [
|
||||||
|
E('h2', {}, [ _('Network Utilities') ]),
|
||||||
|
E('div', { 'class': 'table' }, [
|
||||||
|
E('div', { 'class': 'tr' }, [
|
||||||
|
E('div', { 'class': 'td left' }, [
|
||||||
|
E('input', {
|
||||||
|
'style': 'margin:5px 0',
|
||||||
|
'type': 'text',
|
||||||
|
'value': ping_host
|
||||||
|
}),
|
||||||
|
E('span', { 'class': 'diag-action' }, [
|
||||||
|
has_ping6 ? new ui.ComboButton('ping', {
|
||||||
|
'ping': '%s %s'.format(_('IPv4'), _('Ping')),
|
||||||
|
'ping6': '%s %s'.format(_('IPv6'), _('Ping')),
|
||||||
|
}, {
|
||||||
|
'click': ui.createHandlerFn(this, 'handlePing'),
|
||||||
|
'classes': {
|
||||||
|
'ping': 'cbi-button cbi-button-action',
|
||||||
|
'ping6': 'cbi-button cbi-button-action'
|
||||||
|
}
|
||||||
|
}).render() : E('button', {
|
||||||
|
'class': 'cbi-button cbi-button-action',
|
||||||
|
'click': ui.createHandlerFn(this, 'handlePing')
|
||||||
|
}, [ _('Ping') ])
|
||||||
|
])
|
||||||
|
]),
|
||||||
|
|
||||||
|
E('div', { 'class': 'td left' }, [
|
||||||
|
E('input', {
|
||||||
|
'style': 'margin:5px 0',
|
||||||
|
'type': 'text',
|
||||||
|
'value': route_host
|
||||||
|
}),
|
||||||
|
E('span', { 'class': 'diag-action' }, [
|
||||||
|
has_traceroute6 ? new ui.ComboButton('traceroute', {
|
||||||
|
'traceroute': '%s %s'.format(_('IPv4'), _('Traceroute')),
|
||||||
|
'traceroute6': '%s %s'.format(_('IPv6'), _('Traceroute')),
|
||||||
|
}, {
|
||||||
|
'click': ui.createHandlerFn(this, 'handleTraceroute'),
|
||||||
|
'classes': {
|
||||||
|
'traceroute': 'cbi-button cbi-button-action',
|
||||||
|
'traceroute6': 'cbi-button cbi-button-action'
|
||||||
|
}
|
||||||
|
}).render() : E('button', {
|
||||||
|
'class': 'cbi-button cbi-button-action',
|
||||||
|
'click': ui.createHandlerFn(this, 'handleTraceroute')
|
||||||
|
}, [ _('Traceroute') ])
|
||||||
|
])
|
||||||
|
]),
|
||||||
|
|
||||||
|
E('div', { 'class': 'td left' }, [
|
||||||
|
E('input', {
|
||||||
|
'style': 'margin:5px 0',
|
||||||
|
'type': 'text',
|
||||||
|
'value': dns_host
|
||||||
|
}),
|
||||||
|
E('span', { 'class': 'diag-action' }, [
|
||||||
|
E('button', {
|
||||||
|
'class': 'cbi-button cbi-button-action',
|
||||||
|
'click': ui.createHandlerFn(this, 'handleNslookup')
|
||||||
|
}, [ _('Nslookup') ])
|
||||||
|
])
|
||||||
|
])
|
||||||
|
])
|
||||||
|
]),
|
||||||
|
E('pre', { 'class': 'command-output', 'style': 'display:none' })
|
||||||
|
]);
|
||||||
|
},
|
||||||
|
|
||||||
|
handleSaveApply: null,
|
||||||
|
handleSave: null,
|
||||||
|
handleReset: null
|
||||||
|
});
|
|
@ -66,45 +66,3 @@ function remote_addr()
|
||||||
luci.http.prepare_content("application/json")
|
luci.http.prepare_content("application/json")
|
||||||
luci.http.write_json(result)
|
luci.http.write_json(result)
|
||||||
end
|
end
|
||||||
|
|
||||||
function diag_command(cmd, addr)
|
|
||||||
if addr and addr:match("^[a-zA-Z0-9%-%.:_]+$") then
|
|
||||||
luci.http.prepare_content("text/plain")
|
|
||||||
|
|
||||||
local util = io.popen(cmd % luci.util.shellquote(addr))
|
|
||||||
if util then
|
|
||||||
while true do
|
|
||||||
local ln = util:read("*l")
|
|
||||||
if not ln then break end
|
|
||||||
luci.http.write(ln)
|
|
||||||
luci.http.write("\n")
|
|
||||||
end
|
|
||||||
|
|
||||||
util:close()
|
|
||||||
end
|
|
||||||
|
|
||||||
return
|
|
||||||
end
|
|
||||||
|
|
||||||
luci.http.status(500, "Bad address")
|
|
||||||
end
|
|
||||||
|
|
||||||
function diag_ping(addr)
|
|
||||||
diag_command("ping -c 5 -W 1 %s 2>&1", addr)
|
|
||||||
end
|
|
||||||
|
|
||||||
function diag_traceroute(addr)
|
|
||||||
diag_command("traceroute -q 1 -w 1 -n %s 2>&1", addr)
|
|
||||||
end
|
|
||||||
|
|
||||||
function diag_nslookup(addr)
|
|
||||||
diag_command("nslookup %s 2>&1", addr)
|
|
||||||
end
|
|
||||||
|
|
||||||
function diag_ping6(addr)
|
|
||||||
diag_command("ping6 -c 5 %s 2>&1", addr)
|
|
||||||
end
|
|
||||||
|
|
||||||
function diag_traceroute6(addr)
|
|
||||||
diag_command("traceroute6 -q 1 -w 2 -n %s 2>&1", addr)
|
|
||||||
end
|
|
||||||
|
|
|
@ -1,117 +0,0 @@
|
||||||
<%#
|
|
||||||
Copyright 2010 Jo-Philipp Wich <jow@openwrt.org>
|
|
||||||
Licensed to the public under the Apache License 2.0.
|
|
||||||
-%>
|
|
||||||
|
|
||||||
<%+header%>
|
|
||||||
|
|
||||||
<%
|
|
||||||
local fs = require "nixio.fs"
|
|
||||||
local has_ping6 = fs.access("/bin/ping6") or fs.access("/usr/bin/ping6")
|
|
||||||
local has_traceroute6 = fs.access("/bin/traceroute6") or fs.access("/usr/bin/traceroute6")
|
|
||||||
|
|
||||||
local dns_host = luci.config.diag and luci.config.diag.dns or "dev.openwrt.org"
|
|
||||||
local ping_host = luci.config.diag and luci.config.diag.ping or "dev.openwrt.org"
|
|
||||||
local route_host = luci.config.diag and luci.config.diag.route or "dev.openwrt.org"
|
|
||||||
%>
|
|
||||||
|
|
||||||
<script type="text/javascript">//<![CDATA[
|
|
||||||
var stxhr = new XHR();
|
|
||||||
|
|
||||||
function update_status(field, proto)
|
|
||||||
{
|
|
||||||
var tool = field.name;
|
|
||||||
var addr = field.value;
|
|
||||||
var protocol = proto ? "6" : "";
|
|
||||||
|
|
||||||
var legend = document.getElementById('diag-rc-legend');
|
|
||||||
var output = document.getElementById('diag-rc-output');
|
|
||||||
|
|
||||||
if (legend && output)
|
|
||||||
{
|
|
||||||
output.innerHTML =
|
|
||||||
'<img src="<%=resource%>/icons/loading.gif" alt="<%:Loading%>" style="vertical-align:middle" /> ' +
|
|
||||||
'<%:Waiting for command to complete...%>'
|
|
||||||
;
|
|
||||||
|
|
||||||
legend.parentNode.style.display = 'block';
|
|
||||||
legend.style.display = 'inline';
|
|
||||||
|
|
||||||
stxhr.post('<%=url('admin/network')%>/diag_' + tool + protocol + '/' + addr, { token: '<%=token%>' },
|
|
||||||
function(x)
|
|
||||||
{
|
|
||||||
if (x.responseText)
|
|
||||||
{
|
|
||||||
legend.style.display = 'none';
|
|
||||||
output.innerHTML = String.format('<pre>%h</pre>', x.responseText);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
legend.style.display = 'none';
|
|
||||||
output.innerHTML = '<span class="error"><%:Bad address specified!%></span>';
|
|
||||||
}
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
//]]></script>
|
|
||||||
|
|
||||||
<form method="post" action="<%=url('admin/network/diagnostics')%>">
|
|
||||||
<div class="cbi-map">
|
|
||||||
<h2 name="content"><%:Diagnostics%></h2>
|
|
||||||
|
|
||||||
<div class="cbi-section">
|
|
||||||
<legend><%:Network Utilities%></legend>
|
|
||||||
|
|
||||||
<div class="table">
|
|
||||||
<div class="tr">
|
|
||||||
<div class="td left">
|
|
||||||
<input style="margin: 5px 0" type="text" value="<%=ping_host%>" name="ping" /><br />
|
|
||||||
<% if has_ping6 then %>
|
|
||||||
<span>
|
|
||||||
<select name="ping_proto" style="width:auto">
|
|
||||||
<option value="" selected="selected"><%:IPv4%></option>
|
|
||||||
<option value="6"><%:IPv6%></option>
|
|
||||||
</select>
|
|
||||||
</span>
|
|
||||||
<input type="button" value="<%:Ping%>" class="cbi-button cbi-button-apply" onclick="update_status(this.form.ping, this.form.ping_proto.selectedIndex)" />
|
|
||||||
<% else %>
|
|
||||||
<input type="button" value="<%:Ping%>" class="cbi-button cbi-button-apply" onclick="update_status(this.form.ping)" />
|
|
||||||
<% end %>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="td left">
|
|
||||||
<input style="margin: 5px 0" type="text" value="<%=route_host%>" name="traceroute" /><br />
|
|
||||||
<% if has_traceroute6 then %>
|
|
||||||
<span>
|
|
||||||
<select name="traceroute_proto" style="width:auto">
|
|
||||||
<option value="" selected="selected"><%:IPv4%></option>
|
|
||||||
<option value="6"><%:IPv6%></option>
|
|
||||||
</select>
|
|
||||||
</span>
|
|
||||||
<input type="button" value="<%:Traceroute%>" class="cbi-button cbi-button-apply" onclick="update_status(this.form.traceroute, this.form.traceroute_proto.selectedIndex)" />
|
|
||||||
<% else %>
|
|
||||||
<input type="button" value="<%:Traceroute%>" class="cbi-button cbi-button-apply" onclick="update_status(this.form.traceroute)" />
|
|
||||||
<% end %>
|
|
||||||
<% if not has_traceroute6 then %>
|
|
||||||
<p> </p>
|
|
||||||
<p><%:Install iputils-traceroute6 for IPv6 traceroute%></p>
|
|
||||||
<% end %>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="td left">
|
|
||||||
<input style="margin: 5px 0" type="text" value="<%=dns_host%>" name="nslookup" /><br />
|
|
||||||
<input type="button" value="<%:Nslookup%>" class="cbi-button cbi-button-apply" onclick="update_status(this.form.nslookup)" />
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="cbi-section" style="display:none">
|
|
||||||
<strong id="diag-rc-legend"></strong>
|
|
||||||
<span id="diag-rc-output"></span>
|
|
||||||
</div>
|
|
||||||
</form>
|
|
||||||
|
|
||||||
<%+footer%>
|
|
|
@ -78,53 +78,8 @@
|
||||||
"title": "Diagnostics",
|
"title": "Diagnostics",
|
||||||
"order": 60,
|
"order": 60,
|
||||||
"action": {
|
"action": {
|
||||||
"type": "template",
|
"type": "view",
|
||||||
"path": "admin_network/diagnostics"
|
"path": "network/diagnostics"
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
"admin/network/diag_ping/*": {
|
|
||||||
"action": {
|
|
||||||
"post": true,
|
|
||||||
"type": "call",
|
|
||||||
"module": "luci.controller.admin.network",
|
|
||||||
"function": "diag_ping"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
"admin/network/diag_nslookup/*": {
|
|
||||||
"action": {
|
|
||||||
"post": true,
|
|
||||||
"type": "call",
|
|
||||||
"module": "luci.controller.admin.network",
|
|
||||||
"function": "diag_nslookup"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
"admin/network/diag_traceroute/*": {
|
|
||||||
"action": {
|
|
||||||
"post": true,
|
|
||||||
"type": "call",
|
|
||||||
"module": "luci.controller.admin.network",
|
|
||||||
"function": "diag_traceroute"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
"admin/network/diag_ping6/*": {
|
|
||||||
"action": {
|
|
||||||
"post": true,
|
|
||||||
"type": "call",
|
|
||||||
"module": "luci.controller.admin.network",
|
|
||||||
"function": "diag_ping6"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
"admin/network/diag_traceroute6/*": {
|
|
||||||
"action": {
|
|
||||||
"post": true,
|
|
||||||
"type": "call",
|
|
||||||
"module": "luci.controller.admin.network",
|
|
||||||
"function": "diag_traceroute6"
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue