(threats)
| 4597 | (_wifidef.continuous ? 'Continuous — capturing' : 'Capturing') + (chParam !== 'auto' ? ' ch ' + chParam : '')); |
| 4598 | if (btn) btn.disabled = true; |
| 4599 | return fetch(`/api/wifidef/scan?interface=${encodeURIComponent(iface)}&seconds=${secs}&channel=${chParam}`, |
| 4600 | { signal: ctrl.signal }) |
| 4601 | .then(r => r.json()).then(d => { |
| 4602 | prog.done(); |
| 4603 | if (d.error) { st.textContent = '⚠ ' + d.error; return; } |
| 4604 | _wifidef.monitor = d.monitor || _wifidef.monitor; |
| 4605 | _wifidefUpdateMonBtn(); |
| 4606 | _wifidef.data = d; |
| 4607 | // A fresh WIDS capture invalidates an earlier AI read so it isn't |
| 4608 | // embedded into a report describing a different capture window. |
| 4609 | _wifidef.ai = null; |
| 4610 | st.textContent = `${d.frames} frames · ${new Date(d.timestamp * 1000).toLocaleTimeString()}` |
| 4611 | + (_wifidef.continuous ? ' · live' : ''); |
| 4612 | wifidefRender(); |
| 4613 | }).catch((e) => { |
| 4614 | prog.done(); |
| 4615 | if (e && e.name === 'AbortError') { st.textContent = 'Stopped.'; return; } |
| 4616 | st.textContent = 'Scan failed'; |
| 4617 | }).finally(() => { |
| 4618 | prog.done(); |
no test coverage detected