summaryrefslogtreecommitdiffhomepage
path: root/modules/luci-mod-rpc
diff options
context:
space:
mode:
Diffstat (limited to 'modules/luci-mod-rpc')
-rw-r--r--modules/luci-mod-rpc/Makefile2
-rw-r--r--modules/luci-mod-rpc/luasrc/controller/rpc.lua169
2 files changed, 130 insertions, 41 deletions
diff --git a/modules/luci-mod-rpc/Makefile b/modules/luci-mod-rpc/Makefile
index e64c86c628..bc1f6d2756 100644
--- a/modules/luci-mod-rpc/Makefile
+++ b/modules/luci-mod-rpc/Makefile
@@ -9,6 +9,8 @@ include $(TOPDIR)/rules.mk
LUCI_TITLE:=LuCI RPC - JSON-RPC API
LUCI_DEPENDS:=+luci-lib-json
+PKG_LICENSE:=Apache-2.0
+
include ../../luci.mk
# call BuildPackage - OpenWrt buildroot signature
diff --git a/modules/luci-mod-rpc/luasrc/controller/rpc.lua b/modules/luci-mod-rpc/luasrc/controller/rpc.lua
index 759bb749cf..1e8038b28a 100644
--- a/modules/luci-mod-rpc/luasrc/controller/rpc.lua
+++ b/modules/luci-mod-rpc/luasrc/controller/rpc.lua
@@ -2,80 +2,109 @@
-- Copyright 2008 Jo-Philipp Wich <jow@openwrt.org>
-- Licensed to the public under the Apache License 2.0.
-local require = require
-local pairs = pairs
-local print = print
-local pcall = pcall
-local table = table
+module("luci.controller.rpc", package.seeall)
+
+
+function session_retrieve(sid, allowed_users)
+ local util = require "luci.util"
+ local sdat = util.ubus("session", "get", {
+ ubus_rpc_session = sid
+ })
+
+ if type(sdat) == "table" and
+ type(sdat.values) == "table" and
+ type(sdat.values.token) == "string" and
+ type(sdat.values.secret) == "string" and
+ type(sdat.values.username) == "string" and
+ util.contains(allowed_users, sdat.values.username)
+ then
+ return sid, sdat.values
+ end
-module "luci.controller.rpc"
+ return nil
+end
-function index()
- local function authenticator(validator, accs)
- local auth = luci.http.formvalue("auth", true)
- if auth then -- if authentication token was given
- local sdat = (luci.util.ubus("session", "get", { ubus_rpc_session = auth }) or { }).values
- if sdat then -- if given token is valid
- if sdat.user and luci.util.contains(accs, sdat.user) then
- return sdat.user, auth
- end
- end
+function authenticator(validator, accs)
+ local http = require "luci.http"
+ local ctrl = require "luci.controller.rpc"
+ local auth = http.formvalue("auth", true) or http.getcookie("sysauth")
+
+ if auth then -- if authentication token was given
+ local sid, sdat = ctrl.session_retrieve(auth, accs)
+ if sdat then -- if given token is valid
+ return sdat.username, sid
end
- luci.http.status(403, "Forbidden")
+ http.status(403, "Forbidden")
end
+end
+
+
+function index()
+ local ctrl = require "luci.controller.rpc"
local rpc = node("rpc")
rpc.sysauth = "root"
- rpc.sysauth_authenticator = authenticator
+ rpc.sysauth_authenticator = ctrl.authenticator
rpc.notemplate = true
entry({"rpc", "uci"}, call("rpc_uci"))
entry({"rpc", "fs"}, call("rpc_fs"))
entry({"rpc", "sys"}, call("rpc_sys"))
entry({"rpc", "ipkg"}, call("rpc_ipkg"))
+ entry({"rpc", "ip"}, call("rpc_ip"))
entry({"rpc", "auth"}, call("rpc_auth")).sysauth = false
end
function rpc_auth()
+ local ctrl = require "luci.controller.rpc"
local jsonrpc = require "luci.jsonrpc"
local http = require "luci.http"
local sys = require "luci.sys"
local ltn12 = require "luci.ltn12"
local util = require "luci.util"
- local loginstat
-
local server = {}
server.challenge = function(user, pass)
- local sid, token, secret
-
local config = require "luci.config"
-
- if sys.user.checkpasswd(user, pass) then
- local sdat = util.ubus("session", "create", { timeout = config.sauth.sessiontime })
+ local login = util.ubus("session", "login", {
+ username = user,
+ password = pass,
+ timeout = tonumber(config.sauth.sessiontime)
+ })
+
+ if type(login) == "table" and
+ type(login.ubus_rpc_session) == "string"
+ then
+ util.ubus("session", "set", {
+ ubus_rpc_session = login.ubus_rpc_session,
+ values = {
+ token = sys.uniqueid(16),
+ secret = sys.uniqueid(16)
+ }
+ })
+
+ local sid, sdat = ctrl.session_retrieve(login.ubus_rpc_session, { user })
if sdat then
- sid = sdat.ubus_rpc_session
- token = sys.uniqueid(16)
- secret = sys.uniqueid(16)
-
- http.header("Set-Cookie", "sysauth="..sid.."; path=/")
- util.ubus("session", "set", {
- ubus_rpc_session = sid,
- values = {
- user = user,
- token = token,
- secret = secret
- }
- })
+ return {
+ sid = sid,
+ token = sdat.token,
+ secret = sdat.secret
+ }
end
end
- return sid and {sid=sid, token=token, secret=secret}
+ return nil
end
server.login = function(...)
local challenge = server.challenge(...)
- return challenge and challenge.sid
+ if challenge then
+ http.header("Set-Cookie", 'sysauth=%s; path=%s' %{
+ challenge.sid,
+ http.getenv("SCRIPT_NAME")
+ })
+ return challenge.sid
+ end
end
http.prepare_content("application/json")
@@ -137,13 +166,40 @@ function rpc_fs()
end
function rpc_sys()
+ local util = require "luci.util"
local sys = require "luci.sys"
local jsonrpc = require "luci.jsonrpc"
local http = require "luci.http"
local ltn12 = require "luci.ltn12"
+ local sys2 = util.clone(sys)
+ sys2.net = util.clone(sys.net)
+ sys2.wifi = util.clone(sys.wifi)
+
+ function sys2.wifi.getiwinfo(ifname, operation)
+ local iw = sys.wifi.getiwinfo(ifname)
+ if iw then
+ if operation then
+ assert(type(iwinfo[iw.type][operation]) == "function")
+ return iw[operation]
+ end
+
+ local n, f
+ local rv = { ifname = ifname }
+ for n, f in pairs(iwinfo[iw.type]) do
+ if type(f) == "function" and
+ n ~= "scanlist" and n ~= "countrylist"
+ then
+ rv[n] = iw[n]
+ end
+ end
+ return rv
+ end
+ return nil
+ end
+
http.prepare_content("application/json")
- ltn12.pump.all(jsonrpc.handle(sys, http.source()), http.write)
+ ltn12.pump.all(jsonrpc.handle(sys2, http.source()), http.write)
end
function rpc_ipkg()
@@ -159,3 +215,34 @@ function rpc_ipkg()
http.prepare_content("application/json")
ltn12.pump.all(jsonrpc.handle(ipkg, http.source()), http.write)
end
+
+function rpc_ip()
+ if not pcall(require, "luci.ip") then
+ luci.http.status(404, "Not Found")
+ return nil
+ end
+
+ local util = require "luci.util"
+ local ip = require "luci.ip"
+ local jsonrpc = require "luci.jsonrpc"
+ local http = require "luci.http"
+ local ltn12 = require "luci.ltn12"
+
+ local ip2 = util.clone(ip)
+
+ local _, n
+ for _, n in ipairs({ "new", "IPv4", "IPv6", "MAC" }) do
+ ip2[n] = function(address, netmask, operation, argument)
+ local cidr = ip[n](address, netmask)
+ if cidr and operation then
+ assert(type(cidr[operation]) == "function")
+ local cidr2 = cidr[operation](cidr, argument)
+ return (type(cidr2) == "userdata") and cidr2:string() or cidr2
+ end
+ return (type(cidr) == "userdata") and cidr:string() or cidr
+ end
+ end
+
+ http.prepare_content("application/json")
+ ltn12.pump.all(jsonrpc.handle(ip2, http.source()), http.write)
+end