From 7c5235845a42f9a2c41cc6d3e0ec8f9bc38b1a98 Mon Sep 17 00:00:00 2001 From: liamcottle Date: Sun, 15 Dec 2024 20:51:52 +1300 Subject: [PATCH] add api to scan for ble devices --- meshchat.py | 41 +++++++++++++++++++++++++++++++++++++++++ 1 file changed, 41 insertions(+) diff --git a/meshchat.py b/meshchat.py index d8e31f0..88e27f1 100644 --- a/meshchat.py +++ b/meshchat.py @@ -13,11 +13,13 @@ import RNS import RNS.vendor.umsgpack as msgpack import LXMF from LXMF import LXMRouter +from RNS.Interfaces.RNodeInterface import BLEConnection from aiohttp import web, WSMessage, WSMsgType, WSCloseCode import asyncio import base64 import webbrowser +from bleak import BleakScanner from peewee import SqliteDatabase from serial.tools import list_ports @@ -317,6 +319,45 @@ class ReticulumMeshChat: "comports": comports, }) + # scan for rnodes available via ble + @routes.get("/api/v1/rnodes/ble-scan") + async def index(request): + + # determine how long we should scan for + scan_duration_seconds = int(request.query.get("scan_duration_seconds", 3)) + + # discover ble devices + ble_scan_results = await BleakScanner.discover( + timeout=scan_duration_seconds, + return_adv=True, + cb=dict(use_bdaddr=True), + service_uuids=[ + BLEConnection.UART_SERVICE_UUID, + ], + ) + + # format scan results + rnodes = [] + for ble_address in ble_scan_results: + + # get device and advertisement data from scan result + device, advertisement_data = ble_scan_results[ble_address] + + # skip this result if advertisement data is unavailable + if advertisement_data is None: + continue + + rnodes.append({ + "name": device.name, + "local_name": advertisement_data.local_name, + "ble_address": device.address, + "port": "ble://" + advertisement_data.local_name, + }) + + return web.json_response({ + "rnodes": rnodes, + }) + # fetch reticulum interfaces @routes.get("/api/v1/reticulum/interfaces") async def index(request):