mirror of
https://github.com/smittix/intercept.git
synced 2026-07-08 01:28:13 -07:00
fix: Read WiFi/BT data from v2 scanners in analytics dashboard
The analytics summary, health, and export were only reading from legacy DataStores (app_module.wifi_networks, bt_devices) which the v2 WiFi and Bluetooth scanners don't populate. Now checks v2 scanner singletons first and falls back to legacy stores. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
+33
-8
@@ -89,14 +89,39 @@ def analytics_export(mode: str):
|
|||||||
return jsonify({'status': 'error', 'message': f'Unknown mode: {mode}'}), 400
|
return jsonify({'status': 'error', 'message': f'Unknown mode: {mode}'}), 400
|
||||||
|
|
||||||
all_items: list[dict] = []
|
all_items: list[dict] = []
|
||||||
for store_name in store_names:
|
|
||||||
store = getattr(app_module, store_name, None)
|
# Try v2 scanners first for wifi/bluetooth
|
||||||
if store is None:
|
if mode == 'wifi':
|
||||||
continue
|
try:
|
||||||
for key, value in store.items():
|
from utils.wifi.scanner import _scanner_instance as wifi_scanner
|
||||||
item = dict(value) if isinstance(value, dict) else {'id': key, 'value': value}
|
if wifi_scanner is not None:
|
||||||
item.setdefault('_store', store_name)
|
for ap in wifi_scanner.access_points:
|
||||||
all_items.append(item)
|
all_items.append(ap.to_dict())
|
||||||
|
for client in wifi_scanner.clients:
|
||||||
|
item = client.to_dict()
|
||||||
|
item['_store'] = 'wifi_clients'
|
||||||
|
all_items.append(item)
|
||||||
|
except Exception:
|
||||||
|
pass
|
||||||
|
elif mode == 'bluetooth':
|
||||||
|
try:
|
||||||
|
from utils.bluetooth.scanner import _scanner_instance as bt_scanner
|
||||||
|
if bt_scanner is not None:
|
||||||
|
for dev in bt_scanner.get_devices():
|
||||||
|
all_items.append(dev.to_dict())
|
||||||
|
except Exception:
|
||||||
|
pass
|
||||||
|
|
||||||
|
# Fall back to legacy DataStores if v2 scanners yielded nothing
|
||||||
|
if not all_items:
|
||||||
|
for store_name in store_names:
|
||||||
|
store = getattr(app_module, store_name, None)
|
||||||
|
if store is None:
|
||||||
|
continue
|
||||||
|
for key, value in store.items():
|
||||||
|
item = dict(value) if isinstance(value, dict) else {'id': key, 'value': value}
|
||||||
|
item.setdefault('_store', store_name)
|
||||||
|
all_items.append(item)
|
||||||
|
|
||||||
if fmt == 'csv':
|
if fmt == 'csv':
|
||||||
if not all_items:
|
if not all_items:
|
||||||
|
|||||||
+49
-8
@@ -2,6 +2,7 @@
|
|||||||
|
|
||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
|
||||||
|
import contextlib
|
||||||
import time
|
import time
|
||||||
from collections import deque
|
from collections import deque
|
||||||
from typing import Any
|
from typing import Any
|
||||||
@@ -54,7 +55,7 @@ def get_activity_tracker() -> ModeActivityTracker:
|
|||||||
|
|
||||||
|
|
||||||
def _get_mode_counts() -> dict[str, int]:
|
def _get_mode_counts() -> dict[str, int]:
|
||||||
"""Read current entity counts from app_module DataStores."""
|
"""Read current entity counts from DataStores and v2 scanners."""
|
||||||
counts: dict[str, int] = {}
|
counts: dict[str, int] = {}
|
||||||
try:
|
try:
|
||||||
counts['adsb'] = len(app_module.adsb_aircraft)
|
counts['adsb'] = len(app_module.adsb_aircraft)
|
||||||
@@ -64,14 +65,33 @@ def _get_mode_counts() -> dict[str, int]:
|
|||||||
counts['ais'] = len(app_module.ais_vessels)
|
counts['ais'] = len(app_module.ais_vessels)
|
||||||
except Exception:
|
except Exception:
|
||||||
counts['ais'] = 0
|
counts['ais'] = 0
|
||||||
|
|
||||||
|
# WiFi: prefer v2 scanner, fall back to legacy DataStore
|
||||||
|
wifi_count = 0
|
||||||
try:
|
try:
|
||||||
counts['wifi'] = len(app_module.wifi_networks)
|
from utils.wifi.scanner import _scanner_instance as wifi_scanner
|
||||||
|
if wifi_scanner is not None:
|
||||||
|
wifi_count = len(wifi_scanner.access_points)
|
||||||
except Exception:
|
except Exception:
|
||||||
counts['wifi'] = 0
|
pass
|
||||||
|
if wifi_count == 0:
|
||||||
|
with contextlib.suppress(Exception):
|
||||||
|
wifi_count = len(app_module.wifi_networks)
|
||||||
|
counts['wifi'] = wifi_count
|
||||||
|
|
||||||
|
# Bluetooth: prefer v2 scanner, fall back to legacy DataStore
|
||||||
|
bt_count = 0
|
||||||
try:
|
try:
|
||||||
counts['bluetooth'] = len(app_module.bt_devices)
|
from utils.bluetooth.scanner import _scanner_instance as bt_scanner
|
||||||
|
if bt_scanner is not None:
|
||||||
|
bt_count = len(bt_scanner.get_devices())
|
||||||
except Exception:
|
except Exception:
|
||||||
counts['bluetooth'] = 0
|
pass
|
||||||
|
if bt_count == 0:
|
||||||
|
with contextlib.suppress(Exception):
|
||||||
|
bt_count = len(app_module.bt_devices)
|
||||||
|
counts['bluetooth'] = bt_count
|
||||||
|
|
||||||
try:
|
try:
|
||||||
counts['dsc'] = len(app_module.dsc_messages)
|
counts['dsc'] = len(app_module.dsc_messages)
|
||||||
except Exception:
|
except Exception:
|
||||||
@@ -80,12 +100,19 @@ def _get_mode_counts() -> dict[str, int]:
|
|||||||
|
|
||||||
|
|
||||||
def get_cross_mode_summary() -> dict[str, Any]:
|
def get_cross_mode_summary() -> dict[str, Any]:
|
||||||
"""Return counts dict for all active DataStores."""
|
"""Return counts dict for all active DataStores and v2 scanners."""
|
||||||
counts = _get_mode_counts()
|
counts = _get_mode_counts()
|
||||||
|
wifi_clients_count = 0
|
||||||
try:
|
try:
|
||||||
counts['wifi_clients'] = len(app_module.wifi_clients)
|
from utils.wifi.scanner import _scanner_instance as wifi_scanner
|
||||||
|
if wifi_scanner is not None:
|
||||||
|
wifi_clients_count = len(wifi_scanner.clients)
|
||||||
except Exception:
|
except Exception:
|
||||||
counts['wifi_clients'] = 0
|
pass
|
||||||
|
if wifi_clients_count == 0:
|
||||||
|
with contextlib.suppress(Exception):
|
||||||
|
wifi_clients_count = len(app_module.wifi_clients)
|
||||||
|
counts['wifi_clients'] = wifi_clients_count
|
||||||
return counts
|
return counts
|
||||||
|
|
||||||
|
|
||||||
@@ -111,6 +138,20 @@ def get_mode_health() -> dict[str, dict]:
|
|||||||
running = proc is not None and (proc.poll() is None if proc else False)
|
running = proc is not None and (proc.poll() is None if proc else False)
|
||||||
health[mode] = {'running': running}
|
health[mode] = {'running': running}
|
||||||
|
|
||||||
|
# Override WiFi/BT health with v2 scanner status if available
|
||||||
|
try:
|
||||||
|
from utils.wifi.scanner import _scanner_instance as wifi_scanner
|
||||||
|
if wifi_scanner is not None and wifi_scanner.is_scanning:
|
||||||
|
health['wifi'] = {'running': True}
|
||||||
|
except Exception:
|
||||||
|
pass
|
||||||
|
try:
|
||||||
|
from utils.bluetooth.scanner import _scanner_instance as bt_scanner
|
||||||
|
if bt_scanner is not None and bt_scanner.is_scanning:
|
||||||
|
health['bluetooth'] = {'running': True}
|
||||||
|
except Exception:
|
||||||
|
pass
|
||||||
|
|
||||||
try:
|
try:
|
||||||
sdr_status = app_module.get_sdr_device_status()
|
sdr_status = app_module.get_sdr_device_status()
|
||||||
health['sdr_devices'] = {str(k): v for k, v in sdr_status.items()}
|
health['sdr_devices'] = {str(k): v for k, v in sdr_status.items()}
|
||||||
|
|||||||
Reference in New Issue
Block a user