luci-app-travelmate: remove obsolete option
[project/luci.git] / applications / luci-app-travelmate / htdocs / luci-static / resources / view / travelmate / overview.js
1 'use strict';
2 'require view';
3 'require poll';
4 'require fs';
5 'require ui';
6 'require uci';
7 'require form';
8 'require tools.widgets as widgets';
9
10 /*
11 button handling
12 */
13 function handleAction(ev) {
14 var ifaceValue;
15 if (ev === 'restart') {
16 ifaceValue = String(uci.get('travelmate', 'global', 'trm_iface') || 'trm_wwan');
17 return fs.exec('/etc/init.d/travelmate', ['stop'])
18 .then(fs.exec('/sbin/ifup', [ifaceValue]))
19 .then(fs.exec('/etc/init.d/travelmate', ['start']))
20 }
21 if (ev === 'setup') {
22 ifaceValue = String(uci.get('travelmate', 'global', 'trm_iface') || '');
23 L.ui.showModal(_('Interface Wizard'), [
24 E('p', _('To use Travelmate, you have to set up an uplink interface once. This wizard creates an IPv4- and an IPv6 alias network interface with all required network- and firewall settings.')),
25 E('div', { 'class': 'left', 'style': 'display:flex; flex-direction:column' }, [
26 E('label', { 'class': 'cbi-input-text', 'style': 'padding-top:.5em' }, [
27 E('input', { 'class': 'cbi-input-text', 'id': 'iface', 'placeholder': 'trm_wwan', 'value': ifaceValue, 'maxlength': '15', 'spellcheck': 'false' }),
28 '\xa0\xa0\xa0',
29 _('The uplink interface name')
30 ]),
31 E('label', { 'class': 'cbi-input-text', 'style': 'padding-top:.5em' }, [
32 E('input', { 'class': 'cbi-input-text', 'id': 'zone', 'placeholder': 'wan', 'maxlength': '15', 'spellcheck': 'false' }),
33 '\xa0\xa0\xa0',
34 _('The firewall zone name')
35 ]),
36 E('label', { 'class': 'cbi-input-text', 'style': 'padding-top:.5em' }, [
37 E('input', { 'class': 'cbi-input-text', 'id': 'metric', 'placeholder': '100', 'maxlength': '3', 'spellcheck': 'false' }),
38 '\xa0\xa0\xa0',
39 _('The interface metric')
40 ])
41 ]),
42 E('div', { 'class': 'right' }, [
43 E('button', {
44 'class': 'btn',
45 'click': L.hideModal
46 }, _('Dismiss')),
47 ' ',
48 E('button', {
49 'class': 'cbi-button cbi-button-positive important',
50 'click': ui.createHandlerFn(this, function (ev) {
51 var iface = document.getElementById('iface').value || 'trm_wwan',
52 zone = document.getElementById('zone').value || 'wan',
53 metric = document.getElementById('metric').value || '100';
54 L.resolveDefault(fs.exec('/etc/init.d/travelmate', ['setup', iface, zone, metric]))
55 .then(function (res) {
56 if (res) {
57 ui.addNotification(null, E('p', res.trim() + '.'), 'error');
58 } else {
59 ui.addNotification(null, E('p', _('The uplink interface has been updated.')), 'info');
60 }
61 });
62 L.hideModal();
63 })
64 }, _('Save'))
65 ])
66 ]);
67 return document.getElementById('iface').focus();
68 }
69
70 if (ev === 'qrcode') {
71 return Promise.all([
72 uci.load('wireless')
73 ]).then(function () {
74 var w_sid, w_device, w_ssid, w_enc, w_key, w_hidden, result,
75 w_sections = uci.sections('wireless', 'wifi-iface'),
76 optionsAP = [E('option', { value: '' }, [_('-- AP Selection --')])];
77 for (var i = 0; i < w_sections.length; i++) {
78 if (w_sections[i].mode === 'ap' && w_sections[i].disabled !== '1') {
79 w_sid = i;
80 w_device = w_sections[i].device;
81 w_ssid = w_sections[i].ssid;
82 optionsAP.push(E('option', { value: w_sid }, w_device + ', ' + w_ssid));
83 }
84 }
85 var selectAP = E('select', {
86 id: 'selectID',
87 class: 'cbi-input-select',
88 change: function (ev) {
89 result = document.getElementById('qrcode');
90 if (document.getElementById("selectID").value) {
91 w_sid = document.getElementById("selectID").value;
92 w_ssid = w_sections[w_sid].ssid;
93 w_enc = w_sections[w_sid].encryption;
94 w_key = w_sections[w_sid].key;
95 w_hidden = (w_sections[w_sid].hidden == 1 ? 'true' : 'false');
96 if (w_enc === 'none') {
97 w_enc = 'nopass';
98 w_key = 'nokey';
99 } else {
100 w_enc = 'WPA';
101 }
102 L.resolveDefault(fs.exec_direct('/usr/bin/qrencode', ['--inline', '--8bit', '--type=SVG', '--output=-', 'WIFI:S:' + w_ssid + ';T:' + w_enc + ';P:' + w_key + ';H:' + w_hidden + ';']), null).then(function (res) {
103 if (res) {
104 result.innerHTML = res.trim();
105 }
106 else {
107 result.textContent = _('The QR-Code could not be generated!');
108 }
109 });
110 }
111 else {
112 result.textContent = '';
113 }
114 }
115 }, optionsAP);
116 L.ui.showModal(_('QR-Code Overview'), [
117 E('p', _('Render the QR-Code of the selected Access Point to comfortably transfer the WLAN credentials to your mobile devices.')),
118 E('div', { 'class': 'left', 'style': 'display:flex; flex-direction:column' }, [
119 E('label', { 'class': 'cbi-input-select', 'style': 'padding-top:.5em' }, [
120 selectAP,
121 ])
122 ]),
123 '\xa0',
124 E('div', {
125 'id': 'qrcode'
126 }),
127 E('div', { 'class': 'right' }, [
128 E('button', {
129 'class': 'btn',
130 'click': L.hideModal
131 }, _('Dismiss'))
132 ])
133 ]);
134 });
135 }
136 }
137
138 return view.extend({
139 load: function () {
140 return Promise.all([
141 uci.load('travelmate')
142 ]);
143 },
144
145 render: function (result) {
146 var m, s, o;
147
148 m = new form.Map('travelmate', 'Travelmate', _('Configuration of the travelmate package to enable travel router functionality. \
149 For further information <a href="https://github.com/openwrt/packages/blob/master/net/travelmate/files/README.md" target="_blank" rel="noreferrer noopener" >check the online documentation</a>. <br /> \
150 <em>Please note:</em> On first start please call the \'Interface Wizard\' once, to make the necessary network- and firewall settings.'));
151
152 /*
153 poll runtime information
154 */
155 pollData: poll.add(function () {
156 return L.resolveDefault(fs.stat('/tmp/trm_runtime.json'), null).then(function (res) {
157 var status = document.getElementById('status');
158 if (res && res.size > 0) {
159 L.resolveDefault(fs.read_direct('/tmp/trm_runtime.json'), null).then(function (res) {
160 if (res) {
161 var info = JSON.parse(res);
162 if (status && info) {
163 status.textContent = (info.data.travelmate_status || '-') + ' / ' + (info.data.travelmate_version || '-');
164 if (info.data.travelmate_status.startsWith('running')) {
165 if (!status.classList.contains("spinning")) {
166 status.classList.add("spinning");
167 }
168 } else {
169 if (status.classList.contains("spinning")) {
170 status.classList.remove("spinning");
171 }
172 }
173 } else if (status) {
174 status.textContent = '-';
175 if (status.classList.contains("spinning")) {
176 status.classList.remove("spinning");
177 }
178 }
179 var station_id = document.getElementById('station_id');
180 if (station_id && info) {
181 station_id.textContent = info.data.station_id || '-';
182 }
183 var station_mac = document.getElementById('station_mac');
184 if (station_mac && info) {
185 station_mac.textContent = info.data.station_mac || '-';
186 }
187 var station_interfaces = document.getElementById('station_interfaces');
188 if (station_interfaces && info) {
189 station_interfaces.textContent = info.data.station_interfaces || '-';
190 }
191 var wpa_flags = document.getElementById('wpa_flags');
192 if (wpa_flags && info) {
193 wpa_flags.textContent = info.data.wpa_flags || '-';
194 }
195 var run_flags = document.getElementById('run_flags');
196 if (run_flags && info) {
197 run_flags.textContent = info.data.run_flags || '-';
198 }
199 var ext_hooks = document.getElementById('ext_hooks');
200 if (ext_hooks && info) {
201 ext_hooks.textContent = info.data.ext_hooks || '-';
202 }
203 var run = document.getElementById('run');
204 if (run && info) {
205 run.textContent = info.data.last_run || '-';
206 }
207 }
208 });
209 } else if (status) {
210 status.textContent = '-';
211 if (status.classList.contains("spinning")) {
212 status.classList.remove("spinning");
213 }
214 }
215 });
216 }, 1);
217
218 /*
219 runtime information and buttons
220 */
221 s = m.section(form.NamedSection, 'global');
222 s.render = L.bind(function (view, section_id) {
223 return E('div', { 'class': 'cbi-section' }, [
224 E('h3', _('Information')),
225 E('div', { 'class': 'cbi-value' }, [
226 E('label', { 'class': 'cbi-value-title', 'style': 'padding-top:0rem' }, _('Status / Version')),
227 E('div', { 'class': 'cbi-value-field spinning', 'id': 'status', 'style': 'color:#37c' }, '\xa0')
228 ]),
229 E('div', { 'class': 'cbi-value' }, [
230 E('label', { 'class': 'cbi-value-title', 'style': 'padding-top:0rem' }, _('Station ID')),
231 E('div', { 'class': 'cbi-value-field', 'id': 'station_id', 'style': 'color:#37c' }, '-')
232 ]),
233 E('div', { 'class': 'cbi-value' }, [
234 E('label', { 'class': 'cbi-value-title', 'style': 'padding-top:0rem' }, _('Station MAC')),
235 E('div', { 'class': 'cbi-value-field', 'id': 'station_mac', 'style': 'color:#37c' }, '-')
236 ]),
237 E('div', { 'class': 'cbi-value' }, [
238 E('label', { 'class': 'cbi-value-title', 'style': 'padding-top:0rem' }, _('Station Interfaces')),
239 E('div', { 'class': 'cbi-value-field', 'id': 'station_interfaces', 'style': 'color:#37c' }, '-')
240 ]),
241 E('div', { 'class': 'cbi-value' }, [
242 E('label', { 'class': 'cbi-value-title', 'style': 'padding-top:0rem' }, _('WPA Flags')),
243 E('div', { 'class': 'cbi-value-field', 'id': 'wpa_flags', 'style': 'color:#37c' }, '-')
244 ]),
245 E('div', { 'class': 'cbi-value' }, [
246 E('label', { 'class': 'cbi-value-title', 'style': 'padding-top:0rem' }, _('Run Flags')),
247 E('div', { 'class': 'cbi-value-field', 'id': 'run_flags', 'style': 'color:#37c' }, '-')
248 ]),
249 E('div', { 'class': 'cbi-value' }, [
250 E('label', { 'class': 'cbi-value-title', 'style': 'padding-top:0rem' }, _('Ext. Hooks')),
251 E('div', { 'class': 'cbi-value-field', 'id': 'ext_hooks', 'style': 'color:#37c' }, '-')
252 ]),
253 E('div', { 'class': 'cbi-value' }, [
254 E('label', { 'class': 'cbi-value-title', 'style': 'padding-top:0rem' }, _('Last Run')),
255 E('div', { 'class': 'cbi-value-field', 'id': 'run', 'style': 'color:#37c' }, '-')
256 ]),
257 E('div', { class: 'right' }, [
258 E('button', {
259 'class': 'cbi-button cbi-button-apply',
260 'id': 'btn_suspend',
261 'click': ui.createHandlerFn(this, function () {
262 L.resolveDefault(fs.stat('/usr/bin/qrencode'), null).then(function (res) {
263 if (res) {
264 return handleAction('qrcode');
265 }
266 return ui.addNotification(null, E('p', _('Please install the separate \'qrencode\' package.')), 'info');
267 })
268 })
269 }, [_('AP QR-Codes...')]),
270 '\xa0',
271 E('button', {
272 'class': 'cbi-button cbi-button-negative',
273 'click': ui.createHandlerFn(this, function () {
274 return handleAction('restart');
275 })
276 }, [_('Restart Interface')]),
277 '\xa0',
278 E('button', {
279 'class': 'cbi-button cbi-button-negative',
280 'click': ui.createHandlerFn(this, function () {
281 return handleAction('setup');
282 })
283 }, [_('Interface Wizard...')])
284 ])
285 ]);
286 }, o, this);
287 this.pollData;
288
289 /*
290 tabbed config section
291 */
292 s = m.section(form.NamedSection, 'global', 'travelmate', _('Settings'));
293 s.addremove = false;
294 s.tab('general', _('General Settings'));
295 s.tab('additional', _('Additional Settings'));
296 s.tab('adv_email', _('E-Mail Settings'), _('Please note: E-Mail notifications require the separate setup of the <em>mstmp</em> package.<br /><p>&#xa0;</p>'));
297
298 /*
299 general settings tab
300 */
301 o = s.taboption('general', form.Flag, 'trm_enabled', _('Enabled'), _('Enable the travelmate service.'));
302 o.rmempty = false;
303
304 o = s.taboption('general', form.Flag, 'trm_debug', _('Verbose Debug Logging'), _('Enable verbose debug logging in case of any processing errors.'));
305 o.rmempty = false;
306
307 o = s.taboption('general', form.Value, 'trm_radio', _('Radio Selection'), _('Restrict travelmate to a single radio or change the overall scanning order.'));
308 o.value('radio0', _('use the first radio only (radio0)'));
309 o.value('radio1', _('use the second radio only (radio1)'));
310 o.value('radio0 radio1', _('use both radios, normal sort order (radio0 radio1)'));
311 o.value('radio1 radio0', _('use both radios, reverse sort order (radio1 radio0)'));
312 o.rmempty = true;
313
314 o = s.taboption('general', form.Flag, 'trm_captive', _('Captive Portal Detection'), _('Check the internet availability, handle captive portal redirections and keep the uplink connection \'alive\'.'));
315 o.default = 1;
316 o.rmempty = false;
317
318 o = s.taboption('general', form.Flag, 'trm_vpn', _('VPN processing'), _('VPN connections will be managed by travelmate.'));
319 o.default = 1;
320 o.rmempty = false;
321
322 o = s.taboption('general', widgets.NetworkSelect, 'trm_vpnifacelist', _('Limit VPN processing'), _('Limit VPN processing to certain interfaces.'));
323 o.depends('trm_vpn', '1');
324 o.multiple = true;
325 o.nocreate = true;
326 o.rmempty = true;
327
328 o = s.taboption('general', form.Value, 'trm_stdvpnservice', _('Standard VPN Service'), _('Standard VPN service which will be automatically added to new STA profiles.'));
329 o.depends('trm_vpn', '1');
330 o.value('wireguard');
331 o.value('openvpn');
332 o.rmempty = true;
333
334 o = s.taboption('general', widgets.NetworkSelect, 'trm_stdvpniface', _('Standard VPN interface'), _('Standard VPN interface which will be automatically added to new STA profiles.'));
335 o.depends('trm_vpn', '1');
336 o.nocreate = true;
337 o.rmempty = true;
338
339 o = s.taboption('general', form.Flag, 'trm_netcheck', _('Net Error Check'), _('Treat missing internet availability as an error.'));
340 o.depends('trm_captive', '1');
341 o.default = 0;
342 o.rmempty = false;
343
344 o = s.taboption('general', form.Flag, 'trm_proactive', _('ProActive Uplink Switch'), _('Proactively scan and switch to a higher prioritized uplink, despite of an already existing connection.'));
345 o.default = 1;
346 o.rmempty = false;
347
348 o = s.taboption('general', form.Flag, 'trm_randomize', _('Randomize MAC Addresses'), _('Generate a random unicast MAC address for each uplink connection.'));
349 o.default = 0;
350 o.rmempty = false;
351
352 o = s.taboption('general', form.Flag, 'trm_autoadd', _('AutoAdd Open Uplinks'), _('Automatically add open uplinks like hotel captive portals to your wireless config.'));
353 o.default = 0;
354 o.rmempty = false;
355
356 o = s.taboption('general', form.Value, 'trm_maxautoadd', _('Limit AutoAdd'), _('Limit the maximum number of automatically added open uplinks. To disable this limitation set it to \'0\'.'));
357 o.depends('trm_autoadd', '1');
358 o.placeholder = '5';
359 o.datatype = 'range(0,30)';
360 o.rmempty = true;
361
362 /*
363 additional settings tab
364 */
365 o = s.taboption('additional', form.Value, 'trm_triggerdelay', _('Trigger Delay'), _('Additional trigger delay in seconds before travelmate processing begins.'));
366 o.placeholder = '2';
367 o.datatype = 'range(1,60)';
368 o.rmempty = true;
369
370 o = s.taboption('additional', form.Value, 'trm_maxretry', _('Connection Limit'), _('Retry limit to connect to an uplink.'));
371 o.placeholder = '3';
372 o.datatype = 'range(1,10)';
373 o.rmempty = true;
374
375 o = s.taboption('additional', form.Value, 'trm_minquality', _('Signal Quality Threshold'), _('Minimum signal quality threshold as percent for conditional uplink (dis-) connections.'));
376 o.placeholder = '35';
377 o.datatype = 'range(20,80)';
378 o.rmempty = true;
379
380 o = s.taboption('additional', form.Value, 'trm_maxwait', _('Interface Timeout'), _('How long should travelmate wait for a successful wlan uplink connection.'));
381 o.placeholder = '30';
382 o.datatype = 'range(20,40)';
383 o.rmempty = true;
384
385 o = s.taboption('additional', form.Value, 'trm_timeout', _('Overall Timeout'), _('Overall retry timeout in seconds.'));
386 o.placeholder = '60';
387 o.datatype = 'range(30,300)';
388 o.rmempty = true;
389
390 o = s.taboption('additional', form.ListValue, 'trm_captiveurl', _('Captive Portal URL'), _('The selected URL will be used for connectivity- and captive portal checks.'));
391 o.value('http://detectportal.firefox.com', 'Firefox (default)');
392 o.value('http://connectivity-check.ubuntu.com', 'Ubuntu');
393 o.value('http://captive.apple.com', 'Apple');
394 o.value('http://connectivitycheck.android.com/generate_204', 'Google');
395 o.value('http://www.msftncsi.com/ncsi.txt', 'Microsoft');
396 o.optional = true;
397 o.rmempty = true;
398
399 o = s.taboption('additional', form.ListValue, 'trm_useragent', _('User Agent'), _('The selected user agent will be used for connectivity- and captive portal checks.'));
400 o.value('Mozilla/5.0 (X11; Linux x86_64; rv:109.0) Gecko/20100101 Firefox/118.0', 'Firefox (default)');
401 o.value('Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/118.0.0.0 Safari/537.36', 'Chromium');
402 o.value('Mozilla/5.0 (Macintosh; Intel Mac OS X 14_0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/118.0.0.0 Safari/537.36', 'Safari');
403 o.value('Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/118.0.0.0 Safari/537.36 Edg/118.0.2088.61', 'Edge');
404 o.value('Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/118.0.0.0 Safari/537.36 OPR/103.0.0.0', 'Opera');
405 o.optional = true;
406 o.rmempty = true;
407
408 o = s.taboption('additional', form.ListValue, 'trm_nice', _('Service Priority'), _('The selected priority will be used for travelmate processes.'));
409 o.value('-20', 'Highest Priority');
410 o.value('-10', 'High Priority');
411 o.value('0', 'Normal Priority (default)');
412 o.value('10', 'Less Priority');
413 o.value('19', 'Least Priority');
414 o.optional = true;
415 o.rmempty = true;
416
417 /*
418 advanced email settings tab
419 */
420 o = s.taboption('adv_email', form.Flag, 'trm_mail', _('E-Mail Hook'), _('Sends notification E-Mails after every succesful uplink connect.'));
421 o.rmempty = false;
422
423 o = s.taboption('adv_email', form.Value, 'trm_mailreceiver', _('E-Mail Receiver Address'), _('Receiver address for travelmate notification E-Mails.'));
424 o.depends('trm_mail', '1');
425 o.placeholder = 'name@example.com';
426 o.rmempty = true;
427
428 o = s.taboption('adv_email', form.Value, 'trm_mailsender', _('E-Mail Sender Address'), _('Sender address for travelmate notification E-Mails.'));
429 o.depends({ 'trm_mailreceiver': '@', '!contains': true });
430 o.placeholder = 'no-reply@travelmate';
431 o.rmempty = true;
432
433 o = s.taboption('adv_email', form.Value, 'trm_mailtopic', _('E-Mail Topic'), _('Topic for travelmate notification E-Mails.'));
434 o.depends({ 'trm_mailreceiver': '@', '!contains': true });
435 o.placeholder = 'travelmate connection to \'<station>\'';
436 o.rmempty = true;
437
438 o = s.taboption('adv_email', form.Value, 'trm_mailprofile', _('E-Mail Profile'), _('Profile used by \'msmtp\' for travelmate notification E-Mails.'));
439 o.depends({ 'trm_mailreceiver': '@', '!contains': true });
440 o.placeholder = 'trm_notify';
441 o.rmempty = true;
442
443 return m.render();
444 },
445 handleReset: null
446 });