modules/admin-full: Network interface configuration optimization part #1
This commit is contained in:
parent
0e3fda59e0
commit
07fdaa87db
14 changed files with 184 additions and 124 deletions
|
@ -25,6 +25,7 @@ disable = "disable"
|
||||||
distance = "Distance"
|
distance = "Distance"
|
||||||
dnsserver = "DNS-Server"
|
dnsserver = "DNS-Server"
|
||||||
|
|
||||||
|
edit = "Edit"
|
||||||
enable = "enable"
|
enable = "enable"
|
||||||
encryption = "Encryption"
|
encryption = "Encryption"
|
||||||
error = "Error"
|
error = "Error"
|
||||||
|
|
|
@ -25,6 +25,7 @@ disable = "deaktivieren"
|
||||||
distance = "Distanz"
|
distance = "Distanz"
|
||||||
dnsserver = "DNS-Server"
|
dnsserver = "DNS-Server"
|
||||||
|
|
||||||
|
edit = "Bearbeiten"
|
||||||
enable = "aktivieren"
|
enable = "aktivieren"
|
||||||
encryption = "Verschlüsselung"
|
encryption = "Verschlüsselung"
|
||||||
error = "Fehler"
|
error = "Fehler"
|
||||||
|
|
BIN
libs/cbi/htdocs/luci-static/resources/cbi/edit.gif
Normal file
BIN
libs/cbi/htdocs/luci-static/resources/cbi/edit.gif
Normal file
Binary file not shown.
After Width: | Height: | Size: 280 B |
BIN
libs/cbi/htdocs/luci-static/resources/cbi/remove.gif
Normal file
BIN
libs/cbi/htdocs/luci-static/resources/cbi/remove.gif
Normal file
Binary file not shown.
After Width: | Height: | Size: 385 B |
|
@ -1,18 +0,0 @@
|
||||||
<%#
|
|
||||||
LuCI - Lua Configuration Interface
|
|
||||||
Copyright 2008 Steven Barth <steven@midlink.org>
|
|
||||||
Copyright 2008 Jo-Philipp Wich <xm@leipzig.freifunk.net>
|
|
||||||
|
|
||||||
Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
you may not use this file except in compliance with the License.
|
|
||||||
You may obtain a copy of the License at
|
|
||||||
|
|
||||||
http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
|
|
||||||
$Id$
|
|
||||||
|
|
||||||
-%>
|
|
||||||
|
|
||||||
<%+cbi/valueheader%>
|
|
||||||
<a href="<%=REQUEST_URI%>/<%=section%>"><%:edit%></a>
|
|
||||||
<%+cbi/valuefooter%>
|
|
|
@ -21,36 +21,52 @@ $Id$
|
||||||
<%- local count = 0 -%>
|
<%- local count = 0 -%>
|
||||||
<table class="cbi-section-table">
|
<table class="cbi-section-table">
|
||||||
<tr class="cbi-section-table-titles">
|
<tr class="cbi-section-table-titles">
|
||||||
|
<%- if not self.anonymous then -%>
|
||||||
|
<th> </th>
|
||||||
|
<%- end -%>
|
||||||
<%- for i, k in pairs(self.children) do -%>
|
<%- for i, k in pairs(self.children) do -%>
|
||||||
<th class="cbi-section-table-cell"><%=k.title%></th>
|
<th class="cbi-section-table-cell"><%=k.title%></th>
|
||||||
|
<%- count = count + 1; end; if self.extedit then -%>
|
||||||
|
<th class="cbi-section-table-cell"> </th>
|
||||||
<%- count = count + 1; end; if self.addremove then -%>
|
<%- count = count + 1; end; if self.addremove then -%>
|
||||||
<th class="cbi-section-table-cell"> </th>
|
<th class="cbi-section-table-cell"> </th>
|
||||||
<%- count = count + 1; end -%>
|
<%- count = count + 1; end -%>
|
||||||
</tr>
|
</tr>
|
||||||
<tr class="cbi-section-table-descr">
|
<tr class="cbi-section-table-descr">
|
||||||
|
<%- if not self.anonymous then -%>
|
||||||
|
<th> </th>
|
||||||
|
<%- end -%>
|
||||||
<%- for i, k in pairs(self.children) do -%>
|
<%- for i, k in pairs(self.children) do -%>
|
||||||
<th class="cbi-section-table-cell"><%=k.description%></th>
|
<th class="cbi-section-table-cell"><%=k.description%></th>
|
||||||
|
<%- end; if self.extedit then -%>
|
||||||
|
<th class="cbi-section-table-cell"> </th>
|
||||||
<%- end; if self.addremove then -%>
|
<%- end; if self.addremove then -%>
|
||||||
<th class="cbi-section-table-cell"> </th>
|
<th class="cbi-section-table-cell"> </th>
|
||||||
<%- end -%>
|
<%- end -%>
|
||||||
</tr>
|
</tr>
|
||||||
<%- local isempty = true
|
<%- local isempty = true
|
||||||
for i, k in ipairs(self:cfgsections()) do
|
for i, k in ipairs(self:cfgsections()) do
|
||||||
if not self.anonymous then
|
|
||||||
-%>
|
|
||||||
<tr class="cbi-section-table-title">
|
|
||||||
<th colspan="<%=count%>"><h3><%=k%></h3></th>
|
|
||||||
</tr>
|
|
||||||
<%- end
|
|
||||||
section = k
|
section = k
|
||||||
isempty = false
|
isempty = false
|
||||||
scope = { valueheader = "cbi/cell_valueheader", valuefooter = "cbi/cell_valuefooter" }
|
scope = { valueheader = "cbi/cell_valueheader", valuefooter = "cbi/cell_valuefooter" }
|
||||||
-%>
|
-%>
|
||||||
<tr class="cbi-section-table-row" id="cbi-<%=self.config%>-<%=section%>">
|
<tr class="cbi-section-table-row" id="cbi-<%=self.config%>-<%=section%>">
|
||||||
|
<% if not self.anonymous then -%>
|
||||||
|
<th><h3><%=k%></h3></th>
|
||||||
|
<%- end %>
|
||||||
<%-+cbi/ucisection-%>
|
<%-+cbi/ucisection-%>
|
||||||
|
<%- if self.extedit or self.addremove then -%>
|
||||||
|
<td class="cbi-section-table-cell">
|
||||||
|
<%- if self.extedit then -%>
|
||||||
|
<a href="<%=self.extedit:format(section)%>"><img style="border: none" src="<%=resource%>/cbi/edit.gif" alt="<%:edit%>" /></a>
|
||||||
|
<%- end; if self.addremove then %>
|
||||||
|
<button class="clean" type="submit" value="1" name="cbi.rts.<%=self.config%>.<%=k%>" title="<%:delete%>"><img src="<%=resource%>/cbi/remove.gif" alt="<%:delete%>" /></button>
|
||||||
|
<%- end -%>
|
||||||
|
</td>
|
||||||
|
<%- end -%>
|
||||||
<%- if self.addremove then -%>
|
<%- if self.addremove then -%>
|
||||||
<td class="cbi-section-table-cell">
|
<td class="cbi-section-table-cell">
|
||||||
<input type="submit" name="cbi.rts.<%=self.config%>.<%=k%>" value="X" title="<%:delete%>" />
|
|
||||||
</td>
|
</td>
|
||||||
<%- end -%>
|
<%- end -%>
|
||||||
</tr>
|
</tr>
|
||||||
|
@ -61,9 +77,10 @@ $Id$
|
||||||
<td colspan="<%=count%>"><em><br /><%:cbi_sectempty%></em></td>
|
<td colspan="<%=count%>"><em><br /><%:cbi_sectempty%></em></td>
|
||||||
</tr>
|
</tr>
|
||||||
<%- end -%>
|
<%- end -%>
|
||||||
|
</table>
|
||||||
<%- if self.addremove then -%>
|
<%- if self.addremove then -%>
|
||||||
<tr class="cbi-section-table-row">
|
<br />
|
||||||
|
<div class="cbi-section-table-row">
|
||||||
<td colspan="<%=count%>" class="cbi-section-table-optionals">
|
<td colspan="<%=count%>" class="cbi-section-table-optionals">
|
||||||
<div class="cbi-section-create">
|
<div class="cbi-section-create">
|
||||||
<% if self.anonymous then %>
|
<% if self.anonymous then %>
|
||||||
|
@ -78,9 +95,8 @@ $Id$
|
||||||
<% end %>
|
<% end %>
|
||||||
</div>
|
</div>
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</div>
|
||||||
<%- end -%>
|
<%- end -%>
|
||||||
</table>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<!-- /tblsection -->
|
<!-- /tblsection -->
|
||||||
|
|
|
@ -212,6 +212,21 @@ function net.devices()
|
||||||
return devices
|
return devices
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
|
--- Return information about available network interfaces.
|
||||||
|
-- @return Table containing all current interface names and their information
|
||||||
|
function net.deviceinfo()
|
||||||
|
local devices = {}
|
||||||
|
for line in io.lines("/proc/net/dev") do
|
||||||
|
local name, data = line:match("^ *(.-): *(.*)$")
|
||||||
|
if name and data then
|
||||||
|
devices[name] = luci.util.split(data, " +", nil, true)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
return devices
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
-- Determine the MAC address belonging to the given IP address.
|
-- Determine the MAC address belonging to the given IP address.
|
||||||
-- @param ip IPv4 address
|
-- @param ip IPv4 address
|
||||||
-- @return String containing the MAC address or nil if it cannot be found
|
-- @return String containing the MAC address or nil if it cannot be found
|
||||||
|
|
|
@ -28,35 +28,32 @@ function index()
|
||||||
page.title = i18n("a_n_switch", "Switch")
|
page.title = i18n("a_n_switch", "Switch")
|
||||||
page.order = 10
|
page.order = 10
|
||||||
|
|
||||||
local page = node("admin", "network", "ifaces")
|
local page = node("admin", "network", "network")
|
||||||
page.target = cbi("admin_network/ifaces")
|
page.target = cbi("admin_network/network")
|
||||||
page.title = i18n("interfaces", "Schnittstellen")
|
page.title = i18n("interfaces", "Schnittstellen")
|
||||||
page.order = 20
|
page.order = 20
|
||||||
page.leaf = true
|
|
||||||
|
|
||||||
luci.model.uci.foreach("network", "interface",
|
luci.model.uci.foreach("network", "interface",
|
||||||
function (section)
|
function (section)
|
||||||
local ifc = section[".name"]
|
local ifc = section[".name"]
|
||||||
if ifc ~= "loopback" then
|
if ifc ~= "loopback" then
|
||||||
entry({"admin", "network", "ifaces", ifc},
|
entry({"admin", "network", "network", ifc},
|
||||||
page.target, ifc:upper())
|
alias("admin", "network", "ifaces", ifc),
|
||||||
|
ifc:upper())
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
)
|
)
|
||||||
|
|
||||||
|
local page = node("admin", "network", "ifaces")
|
||||||
|
page.target = cbi("admin_network/ifaces")
|
||||||
|
page.leaf = true
|
||||||
|
|
||||||
local page = node("admin", "network", "dhcp")
|
local page = node("admin", "network", "dhcp")
|
||||||
page.target = cbi("admin_network/dhcp")
|
page.target = cbi("admin_network/dhcp")
|
||||||
page.title = "DHCP"
|
page.title = "DHCP"
|
||||||
page.order = 30
|
page.order = 30
|
||||||
|
|
||||||
local page = node("admin", "network", "ptp")
|
|
||||||
page.target = cbi("admin_network/ptp")
|
|
||||||
page.title = "PPPoE / PPTP"
|
|
||||||
page.order = 40
|
|
||||||
|
|
||||||
local page = node("admin", "network", "routes")
|
local page = node("admin", "network", "routes")
|
||||||
page.target = cbi("admin_network/routes")
|
page.target = cbi("admin_network/routes")
|
||||||
page.title = i18n("a_n_routes", "Routen")
|
page.title = i18n("a_n_routes", "Routen")
|
||||||
page.order = 50
|
page.order = 40
|
||||||
end
|
end
|
|
@ -2,6 +2,7 @@
|
||||||
LuCI - Lua Configuration Interface
|
LuCI - Lua Configuration Interface
|
||||||
|
|
||||||
Copyright 2008 Steven Barth <steven@midlink.org>
|
Copyright 2008 Steven Barth <steven@midlink.org>
|
||||||
|
Copyright 2008 Jo-Philipp Wich <xm@leipzig.freifunk.net>
|
||||||
|
|
||||||
Licensed under the Apache License, Version 2.0 (the "License");
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
you may not use this file except in compliance with the License.
|
you may not use this file except in compliance with the License.
|
||||||
|
@ -11,33 +12,18 @@ You may obtain a copy of the License at
|
||||||
|
|
||||||
$Id$
|
$Id$
|
||||||
]]--
|
]]--
|
||||||
|
arg[1] = arg[1] or ""
|
||||||
|
|
||||||
m = Map("network", translate("interfaces"), translate("a_n_ifaces1"))
|
m = Map("network", translate("interfaces"), translate("a_n_ifaces1"))
|
||||||
|
|
||||||
arg = arg or {}
|
s = m:section(NamedSection, arg[1], "interface", translate("interfaces"))
|
||||||
|
|
||||||
s = m:section(TypedSection, "interface", translate("interfaces"))
|
|
||||||
function s.create(self, section)
|
|
||||||
local stat = TypedSection.create(self, section)
|
|
||||||
if stat then
|
|
||||||
arg = {section or stat}
|
|
||||||
end
|
|
||||||
return stat
|
|
||||||
end
|
|
||||||
|
|
||||||
function s.filter(self, section)
|
|
||||||
return section ~= "loopback" and
|
|
||||||
(not arg or not arg[1] or arg[1] == section)
|
|
||||||
end
|
|
||||||
|
|
||||||
if not arg or not arg[1] then
|
|
||||||
s.addremove = true
|
s.addremove = true
|
||||||
end
|
|
||||||
s:depends("proto", "static")
|
|
||||||
s:depends("proto", "dhcp")
|
|
||||||
|
|
||||||
p = s:option(ListValue, "proto", translate("protocol"))
|
p = s:option(ListValue, "proto", translate("protocol"))
|
||||||
p:value("static", translate("static"))
|
p:value("static", translate("static"))
|
||||||
p:value("dhcp", "DHCP")
|
p:value("dhcp", "DHCP")
|
||||||
|
p:value("pppoe", "PPPoE")
|
||||||
|
p:value("pptp", "PPTP")
|
||||||
p.default = "static"
|
p.default = "static"
|
||||||
|
|
||||||
br = s:option(Flag, "type", translate("a_n_i_bridge"), translate("a_n_i_bridge1"))
|
br = s:option(Flag, "type", translate("a_n_i_bridge"), translate("a_n_i_bridge1"))
|
||||||
|
@ -91,25 +77,38 @@ mtu.isinteger = true
|
||||||
mac = s:option(Value, "macaddr", translate("macaddress"))
|
mac = s:option(Value, "macaddr", translate("macaddress"))
|
||||||
mac.optional = true
|
mac.optional = true
|
||||||
|
|
||||||
|
user = s:option(Value, "username", translate("username"))
|
||||||
|
user.rmempty = true
|
||||||
|
user:depends("proto", "pptp")
|
||||||
|
user:depends("proto", "ppoe")
|
||||||
|
|
||||||
|
pass = s:option(Value, "password", translate("password"))
|
||||||
|
pass.rmempty = true
|
||||||
|
pass:depends("proto", "pptp")
|
||||||
|
pass:depends("proto", "ppoe")
|
||||||
|
|
||||||
|
ka = s:option(Value, "keepalive")
|
||||||
|
ka.rmempty = true
|
||||||
|
ka:depends("proto", "pptp")
|
||||||
|
ka:depends("proto", "ppoe")
|
||||||
|
|
||||||
|
demand = s:option(Value, "demand")
|
||||||
|
demand.rmempty = true
|
||||||
|
demand:depends("proto", "pptp")
|
||||||
|
demand:depends("proto", "ppoe")
|
||||||
|
|
||||||
|
srv = s:option(Value, "server")
|
||||||
|
srv:depends("proto", "pptp")
|
||||||
|
srv.rmempty = true
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
s2 = m:section(TypedSection, "alias", translate("aliases"))
|
s2 = m:section(TypedSection, "alias", translate("aliases"))
|
||||||
s2.addremove = true
|
s2.addremove = true
|
||||||
|
|
||||||
if arg and arg[1] then
|
|
||||||
s2:depends("interface", arg[1])
|
s2:depends("interface", arg[1])
|
||||||
s2.defaults.interface = arg[1]
|
s2.defaults.interface = arg[1]
|
||||||
else
|
|
||||||
parent = s2:option(ListValue, "interface", translate("interface"))
|
|
||||||
luci.model.uci.foreach("network", "interface",
|
|
||||||
function (section)
|
|
||||||
if section[".name"] ~= "loopback" then
|
|
||||||
parent:value(section[".name"])
|
|
||||||
end
|
|
||||||
end
|
|
||||||
)
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
s2.defaults.proto = "static"
|
s2.defaults.proto = "static"
|
||||||
|
|
|
@ -0,0 +1,79 @@
|
||||||
|
--[[
|
||||||
|
LuCI - Lua Configuration Interface
|
||||||
|
|
||||||
|
Copyright 2008 Steven Barth <steven@midlink.org>
|
||||||
|
Copyright 2008 Jo-Philipp Wich <xm@leipzig.freifunk.net>
|
||||||
|
|
||||||
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
you may not use this file except in compliance with the License.
|
||||||
|
You may obtain a copy of the License at
|
||||||
|
|
||||||
|
http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
|
$Id$
|
||||||
|
]]--
|
||||||
|
require("luci.sys")
|
||||||
|
|
||||||
|
|
||||||
|
m = Map("network", translate("interfaces"), translate("a_n_ifaces1"))
|
||||||
|
|
||||||
|
local created
|
||||||
|
local netstat = luci.sys.net.deviceinfo()
|
||||||
|
|
||||||
|
s = m:section(TypedSection, "interface", translate("interfaces"))
|
||||||
|
s.addremove = true
|
||||||
|
s.extedit = luci.http.getenv("REQUEST_URI") .. "/%s"
|
||||||
|
s.template = "cbi/tblsection"
|
||||||
|
|
||||||
|
function s.filter(self, section)
|
||||||
|
return section ~= "loopback" and section
|
||||||
|
end
|
||||||
|
|
||||||
|
function s.create(self, section)
|
||||||
|
if TypedSection.create(self, section) then
|
||||||
|
created = section
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
function s.parse(self, ...)
|
||||||
|
TypedSection.parse(self, ...)
|
||||||
|
if created then
|
||||||
|
luci.http.redirect(luci.http.getenv("REQUEST_URI") .. "/" .. created)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
up = s:option(Flag, "up")
|
||||||
|
up.stateful = true
|
||||||
|
function up.write(self, section, value)
|
||||||
|
local call = value == "1" and "ifdown" or "ifup"
|
||||||
|
os.execute(call .. " " .. section)
|
||||||
|
end
|
||||||
|
|
||||||
|
ipaddr = s:option(DummyValue, "ipaddr", translate("ipaddress"))
|
||||||
|
ipaddr.stateful = true
|
||||||
|
|
||||||
|
function ipaddr.cfgvalue(self, section)
|
||||||
|
local ip = self.map:stateget(section, "ipaddr")
|
||||||
|
local nm = self.map:stateget(section, "netmask")
|
||||||
|
|
||||||
|
local parsed = ip and luci.ip.IPv4(ip, nm)
|
||||||
|
return parsed and parsed:string() or ""
|
||||||
|
end
|
||||||
|
|
||||||
|
rx = s:option(DummyValue, "_rx")
|
||||||
|
|
||||||
|
function rx.cfgvalue(self, section)
|
||||||
|
local ix = self.map:stateget(section, "ifname")
|
||||||
|
local bt = netstat and netstat[ix] and netstat[ix][1]
|
||||||
|
return bt and string.format("%.2f MB", tonumber(bt) / 1024 / 1024)
|
||||||
|
end
|
||||||
|
|
||||||
|
tx = s:option(DummyValue, "_tx")
|
||||||
|
|
||||||
|
function tx.cfgvalue(self, section)
|
||||||
|
local ix = self.map:stateget(section, "ifname")
|
||||||
|
local bt = netstat and netstat[ix] and netstat[ix][9]
|
||||||
|
return bt and string.format("%.2f MB", tonumber(bt) / 1024 / 1024)
|
||||||
|
end
|
||||||
|
|
||||||
|
return m
|
|
@ -1,48 +0,0 @@
|
||||||
--[[
|
|
||||||
LuCI - Lua Configuration Interface
|
|
||||||
|
|
||||||
Copyright 2008 Steven Barth <steven@midlink.org>
|
|
||||||
|
|
||||||
Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
you may not use this file except in compliance with the License.
|
|
||||||
You may obtain a copy of the License at
|
|
||||||
|
|
||||||
http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
|
|
||||||
$Id$
|
|
||||||
]]--
|
|
||||||
m = Map("network", translate("a_n_ptp"), translate("a_n_ptp1"))
|
|
||||||
|
|
||||||
s = m:section(TypedSection, "interface", "")
|
|
||||||
s.addremove = true
|
|
||||||
s:depends("proto", "pppoe")
|
|
||||||
s:depends("proto", "pptp")
|
|
||||||
|
|
||||||
p = s:option(ListValue, "proto", translate("protocol"))
|
|
||||||
p:value("pppoe", "PPPoE")
|
|
||||||
p:value("pptp", "PPTP")
|
|
||||||
p.default = "pppoe"
|
|
||||||
|
|
||||||
ifname = s:option(Value, "ifname", translate("interface"))
|
|
||||||
for i,d in ipairs(luci.sys.net.devices()) do
|
|
||||||
if d ~= "lo" then
|
|
||||||
ifname:value(d)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
s:option(Value, "username", translate("username"))
|
|
||||||
s:option(Value, "password", translate("password"))
|
|
||||||
|
|
||||||
s:option(Value, "keepalive").optional = true
|
|
||||||
|
|
||||||
s:option(Value, "demand").optional = true
|
|
||||||
|
|
||||||
srv = s:option(Value, "server")
|
|
||||||
srv:depends("proto", "pptp")
|
|
||||||
srv.rmempty = true
|
|
||||||
|
|
||||||
mtu = s:option(Value, "mtu", "MTU")
|
|
||||||
mtu.optional = true
|
|
||||||
mtu.isinteger = true
|
|
||||||
|
|
||||||
return m
|
|
|
@ -252,6 +252,12 @@ td input[type=password] {
|
||||||
width: 99%;
|
width: 99%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
button.clean {
|
||||||
|
cursor: pointer;
|
||||||
|
border: none;
|
||||||
|
background-color: inherit;
|
||||||
|
}
|
||||||
|
|
||||||
textarea {
|
textarea {
|
||||||
margin-left: -1px;
|
margin-left: -1px;
|
||||||
margin-bottom: 0.5em;
|
margin-bottom: 0.5em;
|
||||||
|
|
|
@ -237,6 +237,12 @@ td input[type=password] {
|
||||||
width: 99%;
|
width: 99%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
button.clean {
|
||||||
|
cursor: pointer;
|
||||||
|
border: none;
|
||||||
|
background-color: inherit;
|
||||||
|
}
|
||||||
|
|
||||||
textarea {
|
textarea {
|
||||||
margin-left: -1px;
|
margin-left: -1px;
|
||||||
margin-bottom: 0.5em;
|
margin-bottom: 0.5em;
|
||||||
|
|
|
@ -245,6 +245,12 @@ td input[type=password] {
|
||||||
width: 99%;
|
width: 99%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
button.clean {
|
||||||
|
cursor: pointer;
|
||||||
|
border: none;
|
||||||
|
background-color: inherit;
|
||||||
|
}
|
||||||
|
|
||||||
textarea {
|
textarea {
|
||||||
margin-left: -1px;
|
margin-left: -1px;
|
||||||
margin-bottom: 0.5em;
|
margin-bottom: 0.5em;
|
||||||
|
|
Loading…
Reference in a new issue