安装openclash后发现路由器后台没有openclash选项,查看openwrt官网需要配置luci
那就手动配置练习,熟悉一下luci:
输入tree命令观察luci文件目录结构
tree /usr/lib/lua/luci
目录有点多,不过核心就是三个目录,下面用绿色显示
.
├── cacheloader.lua
├── cbi
│ └── datatypes.lua
├── cbi.lua
├── ccache.lua
├── config.lua
├── 'controller'
│ ├── admin
│ │ ├── index.lua
│ │ ├── network.lua
│ │ └── uci.lua
│ ├── firewall.lua
│ ├── myapp
│ │ └── mymodule.lua
│ └── opkg.lua
├── debug.lua
├── dispatcher.lua
├── http.lua
├── i18n.lua
├── ip.so
├── jsonc.so
├── ltn12.lua
├──'model'
│ ├── 'cbi'
│ │ ├── admin_system
│ │ │ └── backupfiles.lua
│ │ └── myapp-mymodule
│ │ └── netifaces.lua
│ ├── firewall.lua
│ ├── myapp-mymodule
│ │ ├── gateway_sn.lua
│ │ └── netifaces.lua
│ ├── network
│ │ ├── proto_3g.lua
│ │ ├── proto_4x6.lua
│ │ ├── proto_6x4.lua
│ │ ├── proto_dhcpv6.lua
│ │ ├── proto_hnet.lua
│ │ ├── proto_ipip.lua
│ │ ├── proto_modemmanager.lua
│ │ ├── proto_ncm.lua
│ │ ├── proto_openconnect.lua
│ │ ├── proto_ppp.lua
│ │ ├── proto_pppossh.lua
│ │ ├── proto_qmi.lua
│ │ ├── proto_relay.lua
│ │ ├── proto_vpnc.lua
│ │ └── proto_wireguard.lua
│ ├── network.lua
│ └── uci.lua
├── sgi
│ ├── cgi.lua
│ └── uhttpd.lua
├── store.lua
├── sys
│ ├── zoneinfo
│ │ ├── tzdata.lua
│ │ └── tzoffset.lua
│ └── zoneinfo.lua
├── sys.lua
├── template
│ └── parser.so
├── template.lua
├── tools
│ └── webadmin.lua
├── util.lua
├── version.lua
└── 'view'
├── admin_status
│ └── index.htm
├── cbi
│ ├── browser.htm
│ ├── button.htm
│ ├── cell_valuefooter.htm
│ ├── cell_valueheader.htm
│ ├── compound.htm
│ ├── delegator.htm
│ ├── dropdown.htm
│ ├── dvalue.htm
│ ├── dynlist.htm
│ ├── error.htm
│ ├── firewall_zonelist.htm
│ ├── footer.htm
│ ├── full_valuefooter.htm
│ ├── full_valueheader.htm
│ ├── fvalue.htm
│ ├── header.htm
│ ├── ipaddr.htm
│ ├── lvalue.htm
│ ├── map.htm
│ ├── mvalue.htm
│ ├── network_ifacelist.htm
│ ├── network_netinfo.htm
│ ├── network_netlist.htm
│ ├── nsection.htm
│ ├── nullsection.htm
│ ├── simpleform.htm
│ ├── tabcontainer.htm
│ ├── tblsection.htm
│ ├── tsection.htm
│ ├── tvalue.htm
│ ├── ucisection.htm
│ ├── upload.htm
│ ├── value.htm
│ ├── valuefooter.htm
│ ├── valueheader.htm
│ └── wireless_modefreq.htm
├── csrftoken.htm
├── empty_node_placeholder.htm
├── error404.htm
├── error500.htm
├── footer.htm
├── header.htm
├── helloworld.htm
├── indexer.htm
├── myapp-mymodule
│ └── helloworld.htm
├── opkg.htm
├── sysauth.htm
├── themes
│ └── bootstrap
│ ├── footer.htm
│ └── header.htm
└── view.htm
luci对应MVP模型
对应上面三个目录
在上面controller文件下新建文件夹myapp及mymoudle.lua
cd /usr/lib/lua/luci/controller
mkdir -p myapp
vi mymoudle.lua
在创建的文件中写下lua脚本
function index()
entry({"admin","vpn","openclash"},call("action_try"),"OpenClash",10).dependent=false
entry({"admin","vpn","template"},template("myapp-mymodule/helloworld"),"OpenClashT",20).dependent=false
entry({"admin", "vpn", "interfaces"}, cbi("myapp-mymodule/netifaces"), "Network interfaces", 30).dependent=false
end
function action_try()
luci.http.prepare_content("text/plain")
luci.http.write("just for test")
luci.http.write(luci.dispatcher.build_url("ui/"))
luci.http.redirect(luci.dispatcher.build_url("192.168.1.1:9999/ui/"))
end
这个时候路由器后台还不会显示,reboot后
reboot
登陆后台发现多出了VPN相关子选项:
基本上每次更新view、control、model,注意清理luci-modulecache
rm -rf /tmp/luci-modulecache/
官方文档给出entry解释:
entry(path, target, title=nil, order=nil)
path是描述调度树中位置的表:例如,{"foo", "bar", "baz"}将在 中插入您的节点的路径foo.bar.baz。
target描述当用户请求节点时将采取的操作。有几个预定义的,其中最重要的 3 个(调用、模板、cbi)
title 定义用户在菜单中可见的标题(可选)
order 是一个数字,同级别的节点将在菜单中排序(可选)
上面mymoudle.lua 中即entry对应target三个预定义
call即是调用脚本内函数
template是调用view文件下自定义html模板下面将创建
cbi系统配置可以直接在后台配相关text,radio等图形化设置。
下面解释entry三项:
第一项:
entry({"admin","vpn","openclash"},call("action_try"),"OpenClash",10).dependent=false
很简单就是调用脚本里面action_try函数显示效果为:
第二项:也是配置openclash项目,其实第一项也可以直接配置。
entry({"admin","vpn","template"},template("myapp-mymodule/helloworld"),"OpenClashT",20).dependent=false
需要在 /usr/lib/lua/luci/view建立相关html模板 (目录和文件随便建保证和entry中对应即可)
cd /usr/lib/lua/luci/view
mkdir -p mymodule && cd mymodule
vi helloworld.htm
创建htm模板
<%+header%>
<h1><%: CLASH CONFIG %></h1>
<a href="http://192.168.1.1:9999/ui/"><%: OpenClash %> </a>
<%+footer%>
href中填入openclash配置好的地址即可
删除一下cache:
rm -rf /tmp/luci-modulecache/
路由器后台刷新观察:
点击后跳转到clash配置界面
成功配置了openclash
第三项:
entry({"admin", "vpn", "interfaces"}, cbi("myapp-mymodule/netifaces"), "Network interfaces", 30).dependent=false
配置cbi比较复杂,根据官方教程:
进入model目录创建相关cgi配置
cd /usr/lib/lua/luci//model
mkdir -p myapp-mymodule && cd myapp-mymodule
vi netifaces.lua
文件和目录都可以随便创建和entry对应即可
lua脚本:
m = Map("network", "Network") -- We want to edit the uci config file /etc/config/network
s = m:section(TypedSection, "interface", "Interfaces") -- Especially the "interface"-sections
s.addremove = true -- Allow the user to create and remove the interfaces
function s:filter(value)
return value ~= "loopback" and value -- Don't touch loopback
end
s:depends("proto", "static") -- Only show those with "static"
s:depends("proto", "dhcp") -- or "dhcp" as protocol and leave PPPoE and PPTP alone
p = s:option(ListValue, "proto", "Protocol") -- Creates an element list (select box)
p:value("static", "static") -- Key and value pairs
p:value("dhcp", "DHCP")
p.default = "static"
s:option(Value, "ifname", "interface", "the physical interface to be used") -- This will give a simple textbox
s:option(Value, "ipaddr", translate("ip", "IP Address")) -- Yes, this is an i18n function ;-)
s:option(Value, "netmask", "Netmask"):depends("proto", "static") -- You may remember this "depends" function from above
mtu = s:option(Value, "mtu", "MTU")
mtu.optional = true -- This one is very optional
dns = s:option(Value, "dns", "DNS-Server")
dns:depends("proto", "static")
dns.optional = true
function dns:validate(value) -- Now, that's nifty, eh?
return value:match("[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+") -- Returns nil if it doesn't match otherwise returns match
end
gw = s:option(Value, "gateway", "Gateway")
gw:depends("proto", "static")
gw.rmempty = true -- Remove entry if it is empty
return m -- Returns the map
输入完脚本后删除一下cache:
rm -rf /tmp/luci-modulecache/
点击NetWork interfaces
报错:
/usr/lib/lua/luci/dispatcher.lua:938: module 'luci.cbi' not found:
no field package.preload['luci.cbi']
no file './luci/cbi.lua'
no file '/usr/share/lua/luci/cbi.lua'
no file '/usr/share/lua/luci/cbi/init.lua'
no file '/usr/lib/lua/luci/cbi.lua'
no file '/usr/lib/lua/luci/cbi/init.lua'
no file './luci/cbi.so'
no file '/usr/lib/lua/luci/cbi.so'
no file '/usr/lib/lua/loadall.so'
no file './luci.so'
no file '/usr/lib/lua/luci.so'
no file '/usr/lib/lua/loadall.so'
stack traceback:
bash下安装相关库
opkg update
opkg install luci luci-base luci-compat
路由器后台刷新:
经过练习一下,对luci有了一个基本认识。