Merge pull request #1818 from dibdot/lxc_fix
[project/luci.git] / applications / luci-app-splash / luasrc / view / admin_status / splash.htm
1 <%#
2  Copyright 2009 Jo-Philipp Wich <jow@openwrt.org>
3  Licensed to the public under the Apache License 2.0.
4 -%>
5
6 <%-
7
8 local utl = require "luci.util"
9 local sys = require "luci.sys"
10 local ipc = require "luci.ip"
11 local ipt = require "luci.sys.iptparser".IptParser()
12 local uci = require "luci.model.uci".cursor_state()
13 local wat = require "luci.tools.webadmin"
14 local ipc = require "luci.ip"
15 local fs  = require "nixio.fs"
16
17 local clients = { }
18 local leasetime = tonumber(uci:get("luci_splash", "general", "leasetime") or 1) * 60 * 60
19
20 uci:foreach("luci_splash_leases", "lease",
21         function(s)
22                 local m = ipc.checkmac(s.mac)
23                 if m and s.start then
24                         clients[m] = {
25                                 start   = tonumber(s.start),
26                                 limit   = ( tonumber(s.start) + leasetime ),
27                                 mac     = m,
28                                 ipaddr  = s.ipaddr,
29                                 policy  = "normal",
30                                 packets = 0,
31                                 bytes   = 0,
32                         }
33                 end
34         end)
35
36 for _, r in ipairs(ipt:find({table="nat", chain="luci_splash_leases"})) do
37         if r.options and #r.options >= 2 and r.options[1] == "MAC" then
38                 local m = ipc.checkmac(r.options[2])
39                 if m and not clients[m] then
40                         clients[m] = {
41                                 start  = 0,
42                                 limit  = 0,
43                                 mac    = m,
44                                 policy = ( r.target == "RETURN" ) and "whitelist" or "blacklist",
45                                 packets = 0,
46                                 bytes   = 0
47                         }
48                 end
49         end
50 end
51
52 for mac, client in pairs(clients) do
53         client.bytes_in    = 0
54         client.bytes_out   = 0
55         client.packets_in  = 0
56         client.packets_out = 0
57
58         if client.ipaddr then
59                 local rin  = ipt:find({table="mangle", chain="luci_splash_mark_in", destination=client.ipaddr})
60                 local rout = ipt:find({table="mangle", chain="luci_splash_mark_out", options={"MAC", client.mac}})
61
62                 if rin and #rin > 0 then
63                         client.bytes_in   = rin[1].bytes
64                         client.packets_in = rin[1].packets
65                 end
66
67                 if rout and #rout > 0 then
68                         client.bytes_out   = rout[1].bytes
69                         client.packets_out = rout[1].packets
70                 end
71         end
72 end
73
74 uci:foreach("luci_splash", "whitelist",
75         function(s)
76                 local m = ipc.checkmac(s.mac)
77                 if m and clients[m] then
78                         clients[m].policy="whitelist"
79                 end
80         end)
81
82 uci:foreach("luci_splash", "blacklist",
83         function(s)
84                 local m = ipc.checkmac(s.mac)
85                 if m and clients[m] then
86                         clients[m].policy=(s.kicked and "kicked" or "blacklist")
87                 end
88         end)            
89
90 sys.net.host_hints(function(mac, v4, v6, name)
91         local c = mac and clients[mac]
92         if c then
93                 c.ip = c.ip or v4
94                 c.hostname = c.hostname or name
95         end
96 end)
97
98 local function showmac(mac)
99         if not is_admin then
100                 mac = mac:gsub("(%S%S:%S%S):%S%S:%S%S:(%S%S:%S%S)", "%1:XX:XX:%2")
101         end
102         return mac
103 end
104
105 if luci.http.formvalue("status") == "1" then
106         local rv = {}
107         for _, c in utl.spairs(clients,
108                 function(a,b) if clients[a].policy == clients[b].policy then
109                         return (clients[a].start > clients[b].start)
110                 else
111                         return (clients[a].policy > clients[b].policy)
112                 end
113         end)
114         do
115                 if c.ip then
116                         rv[#rv+1] = {
117                                 hostname = c.hostname or "?",
118                                 ip = c.ip or "?",
119                                 mac = showmac(c.mac) or "?",
120                                 timeleft = (c.limit >= os.time()) and wat.date_format(c.limit-os.time()) or (c.policy ~= "normal") and "-" or "expired",
121                                 trafficin = wat.byte_format(c.bytes_in) or "?",
122                                 trafficout = wat.byte_format(c.bytes_out) or "?",
123                                 policy = c.policy or "?"
124                                 }
125                 end
126         end
127         luci.http.prepare_content("application/json")
128         luci.http.write_json(rv)
129         return
130 end
131 -%>
132
133
134
135 <%+header%>
136
137 <script type="text/javascript" src="<%=resource%>/cbi.js"></script>
138 <script type="text/javascript">//<![CDATA[
139
140         XHR.poll(10 , '<%=REQUEST_URI%>', { status: 1 },
141                 function(x, info)
142                 {
143                 var tbody = document.getElementById('splash_table');
144                         if (tbody)
145                         {
146                                 var s = '';
147                                 if (info.length == undefined) {
148                                         s += '<tr class="cbi-section-table-row"><td colspan="7" class="cbi-section-table-cell"><br /><em><%:No clients connected%></em><br /></td></tr>'
149                                 };
150                                 for (var idx = 0; idx < info.length; idx++)
151                                 {
152                                         var splash = info[idx];
153                                         s += String.format(
154                                                 '<tr class="cbi-section-table-row cbi-rowstyle-'+(1 + (idx % 2))+'">' +
155                                                 '<td class="cbi-section-table-cell">%s</td>' +
156                                                 '<td class="cbi-section-table-cell">%s</td>' +
157                                                 '<td class="cbi-section-table-cell">%s</td>' +
158                                                 '<td class="cbi-section-table-cell">%s</td>' +
159                                                 '<td class="cbi-section-table-cell">%s/%s</td>' +
160                                                 '<td class="cbi-section-table-cell">',
161                                                 splash.hostname, splash.ip, splash.mac, splash.timeleft, splash.trafficin, splash.trafficout);
162
163                                 <% if is_admin then %>
164                                         s += String.format('<select name="policy.%s" style="width:200px">', splash.mac);
165                                         if (splash.policy == 'whitelist') {     
166                                                 s += '<option value="whitelist" selected="selected"><%:whitelisted%></option>'
167                                         } else {
168                                                 s += '<option value="whitelist"><%:whitelisted%></option>'
169                                         };
170                                         if (splash.policy == 'normal') {
171                                                 s += '<option value="normal" selected="selected"><%:splashed%></option>';
172                                                 s += '<option value="kicked"><%:temporarily blocked%></option>'
173                                         } else {
174                                                 s += '<option value="normal"><%:splashed%></option>'
175                                         };
176                                         if (splash.policy == 'blacklist') {
177                                                 s+= '<option value="blacklist" selected="selected"><%:blacklisted%></option>'
178                                         } else {
179                                                 s += '<option value="blacklist"><%:blacklisted%></option>'
180                                         };
181                                         s += String.format(
182                                                 '</select>' +
183                                                 '<input type="submit" class="cbi-button cbi-button-save" name="save.%s" value="<%:Save%>" />',
184                                                 splash.mac);
185                                 <% else %>
186                                         s += String.format('%s', splash.policy);
187                                 <% end %>
188                                         s += '</td></tr>'
189                                 }
190                                 tbody.innerHTML = s;
191                         }
192                 }
193         );
194 //]]></script>
195
196
197 <div id="cbi-splash-leases" class="cbi-map">
198         <h2 name="content"><%:Client-Splash%></h2>
199         <fieldset id="cbi-table-table" class="cbi-section">
200                 <legend><%:Active Clients%></legend>
201                 <div class="cbi-section-node">
202                         <% if is_admin then %><form action="<%=REQUEST_URI%>" method="post"><input type="hidden" name="token" value="<%=token%>" /><% end %>
203                         <table class="cbi-section-table">
204                                 <thead>
205                                         <tr class="cbi-section-table-titles">
206                                                 <th class="cbi-section-table-cell"><%:Hostname%></th>
207                                                 <th class="cbi-section-table-cell"><%:IP Address%></th>
208                                                 <th class="cbi-section-table-cell"><%:MAC Address%></th>
209                                                 <th class="cbi-section-table-cell"><%:Time remaining%></th>
210                                                 <th class="cbi-section-table-cell"><%:Traffic in/out%></th>
211                                                 <th class="cbi-section-table-cell"><%:Policy%></th>
212                                         </tr>
213                                 </thead>
214                                 <tbody id="splash_table">
215
216                                 <%-
217                                         local count = 0
218                                         for _, c in utl.spairs(clients,
219                                                 function(a,b)
220                                                         if clients[a].policy == clients[b].policy then
221                                                                 return (clients[a].start > clients[b].start)
222                                                         else
223                                                                 return (clients[a].policy > clients[b].policy)
224                                                         end
225                                                 end)
226                                         do
227                                                 if c.ip then
228                                                         count = count + 1
229                                 -%>
230                                                 <tr class="cbi-section-table-row cbi-rowstyle-<%=2-(count%2)%>">
231                                                 <td class="cbi-section-table-cell"><%=c.hostname or "<em>" .. translate("unknown") .. "</em>"%></td>
232                                                 <td class="cbi-section-table-cell"><%=c.ip or "<em>" .. translate("unknown") .. "</em>"%></td>
233                                                 <td class="cbi-section-table-cell"><%=showmac(c.mac)%></td>
234                                                 <td class="cbi-section-table-cell"><%=
235                                                         (c.limit >= os.time()) and wat.date_format(c.limit-os.time()) or
236                                                                 (c.policy ~= "normal") and "-" or "<em>" .. translate("expired") .. "</em>"
237                                                 %></td>
238                                                 <td class="cbi-section-table-cell"><%=wat.byte_format(c.bytes_in)%> / <%=wat.byte_format(c.bytes_out)%></td>
239                                                 <td class="cbi-section-table-cell">
240                                                         <% if is_admin then %>
241                                                         <select name="policy.<%=c.mac:lower()%>" style="width:200px">
242                                                                 <option value="whitelist"<%=c.policy=="whitelist" and ' selected="selected"'%>><%:whitelisted%></option>
243                                                                 <option value="normal"<%=c.policy=="normal" and not c.kicked and ' selected="selected"'%>><%:splashed%></option>
244                                                                 <option value="blacklist"<%=c.policy=="blacklist" and ' selected="selected"'%>><%:blacklisted%></option>
245                                                                 <% if c.policy == "normal" then -%>
246                                                                         <option value="kicked"><%:temporarily blocked%></option>
247                                                                 <%- end %>
248                                                         </select>
249                                                         <input type="submit" class="cbi-button cbi-button-save" name="save.<%=c.mac:lower()%>" value="<%:Save%>" />
250                                                         <% else %>
251                                                         <%=c.policy%>
252                                                         <% end %>
253                                                 </td>
254                                                 </tr>
255                                                 <%- 
256                                                         end
257                                                 end
258                                                 if count == 0 then
259                                                 -%>
260                                                 <tr class="cbi-section-table-row">
261                                                         <td colspan="7" class="cbi-section-table-cell">
262                                                                 <br /><em><%:No clients connected%></em><br />
263                                                         </td>
264                                                 </tr>
265                                 <%- end -%>
266                                 </tbody>
267                         </table>
268                         <% if is_admin then %></form><% end %>
269                 </div>
270         </fieldset>
271 </div>
272
273 <%+footer%>