Mobile App¶
Die Mobile App wird mit React Native und Expo entwickelt und ermöglicht die Kommunikation mit IoT-Geräten über BLE und MQTT.
Geräte suchen und verbinden¶
Beim Start eines Scans sucht die App gezielt nach Geräten, die den im Thing Model hinterlegten BLE-Service anbieten. Auf Android und iOS läuft dieser Vorgang als nativer BLE-Scan. In der Web-Version öffnet der Browser einen eigenen Geräteauswahldialog über Web Bluetooth.
Gefundene Produkte werden in der App angezeigt. Wenn ein gefundenes Produkt zu einem registrierten Thing passt, kann es als Vorschlag markiert werden. Dadurch erkennt der Nutzer schneller, welches physische Produkt zu welchem Eintrag in der App gehört.
Beim Verbinden wird für jedes Thing eine eigene Verbindung verwaltet. Die App kann dadurch mehrere Produkte parallel per BLE unterstützen. Bestehende Verbindungen anderer Produkte bleiben erhalten, während eine neue Verbindung aufgebaut oder eine einzelne Verbindung getrennt wird.
Damit ein neues Produkt überhaupt in der App erscheint, muss es zunächst als Thing angelegt werden. Dazu wählt man in der App „Geräte hinzufügen" → „Per Geräte-ID hinzufügen" und gibt die Geräte-ID sowie den Pairing-Code des Produkts ein. Der Pairing-Code besteht aus den letzten vier Stellen der MAC-Adresse und wird beim Provisioning auf der Weboberfläche des Access Points bzw. über den seriellen Monitor angezeigt. Erst nach dieser Zuordnung kann die App das physische Produkt einem Eintrag zuordnen und eine Verbindung per BLE aufbauen.
BLE in der App¶
Neben der BLE-Implementierung auf dem ESP32 wurde auch in der App eine BLE-Anbindung umgesetzt. Während der ESP32 als BLE-Server arbeitet, übernimmt die App die Rolle des BLE-Clients. Sie sucht nach passenden Geräten, stellt eine Verbindung her, sendet Steuerbefehle und empfängt aktuelle Telemetrie-Daten.
Plattformübergreifende BLE-Unterstützung¶
Die App ist so aufgebaut, dass BLE sowohl auf mobilen Geräten als auch im Web genutzt werden kann. Für Android und iOS wird die native BLE-Unterstützung über react-native-ble-plx verwendet. Für die Web-Version wird die Web-Bluetooth-Schnittstelle des Browsers genutzt.
Dadurch kann dieselbe Grundlogik für verschiedene Plattformen verwendet werden. Die App prüft dabei zuerst, ob BLE auf der jeweiligen Plattform verfügbar ist. Auf mobilen Geräten wird zusätzlich kontrolliert, ob Bluetooth eingeschaltet und bereit ist. Auf Android werden außerdem die notwendigen Berechtigungen angefragt, da BLE-Scans je nach Android-Version unterschiedliche Rechte benötigen.
WLAN-Provisioning über BLE¶
Zusätzlich zur normalen BLE-Kommunikation unterstützt die App auch ein WLAN-Provisioning über BLE. Dieses wird verwendet, wenn ein neues Gerät noch nicht mit einem WLAN verbunden ist.
In diesem Fall verbindet sich die App zunächst per BLE mit dem Gerät und überträgt die WLAN-Zugangsdaten. Das Gerät kann sich anschließend mit dem WLAN verbinden und danach über den ConnectHub beziehungsweise MQTT kommunizieren.
Für dieses Provisioning wird ein eigenes BLE-Profil verwendet, das unabhängig vom normalen Thing-BLE-Profil ist. Die App sendet dabei die SSID und das Passwort an das Gerät. Der ESP32 antwortet mit einer Erfolgsmeldung oder einer Fehlermeldung.
Eine Besonderheit ist, dass der ESP32 nach erfolgreichem Empfang der WLAN-Daten die BLE-Verbindung bewusst beenden kann, um sich mit dem WLAN zu verbinden. Die App berücksichtigt dieses Verhalten und kann einen erwarteten Disconnect in diesem Ablauf als erfolgreichen Provisioning-Schritt behandeln.
BLE-Profil eines Things¶
Jedes Gerät kann im Thing Model ein eigenes BLE-Profil besitzen. Dieses Profil enthält die UUID des BLE-Services sowie die UUIDs der RX- und TX-Characteristics. Die RX-Characteristic wird von der App genutzt, um Befehle an den ESP32 zu senden. Die TX-Characteristic wird verwendet, um Daten vom ESP32 zu empfangen.
Damit die Verbindung funktioniert, müssen die UUIDs in der App, im Thing Model und auf dem ESP32 exakt übereinstimmen. Hat ein Thing kein BLE-Profil, kann die App für dieses Gerät keinen BLE-Scan starten. Dadurch wird verhindert, dass Geräte verbunden werden, für die keine passende BLE-Konfiguration vorhanden ist.
Befehle an den ESP32 senden¶
Sobald ein Gerät verbunden ist, kann die App Befehle über BLE an den ESP32 senden. Dafür schreibt sie ein JSON-Payload auf die RX-Characteristic des Geräts.
Ein Befehl besteht aus einer Capability und einem Wert. Die Capability beschreibt, welcher Zustand oder welche Funktion geändert werden soll. Der Wert enthält die neue Einstellung. Ein Beispiel dafür ist die Änderung der LED-Helligkeit über die Capability brightness.
Wichtig ist, dass die Capability-Namen exakt mit dem Thing Model und dem ESP32-Code übereinstimmen. Wenn die App beispielsweise brightness sendet, muss auch der ESP32 diese Capability erkennen und verarbeiten können. Nur so kann ein Befehl aus der App korrekt auf dem Gerät ausgeführt werden.
Telemetrie über BLE empfangen¶
Die App empfängt aktuelle Gerätedaten über die TX-Characteristic des ESP32. Dafür wird nach dem Verbinden eine Notify-Subscription gestartet. Sobald der ESP32 neue Werte sendet, werden diese automatisch an die App übertragen.
Die empfangenen Daten werden in der App ausgewertet und an andere Bereiche der Anwendung weitergegeben. Dadurch können Live-Werte wie Sensorwerte, LED-Zustand oder Helligkeit direkt in der Benutzeroberfläche angezeigt werden.
Die App unterstützt dabei verschiedene JSON-Formate. Einzelne Werte können als Capability-Value-Paar übertragen werden. Alternativ kann der ESP32 mehrere Werte gleichzeitig als Objekt senden, zum Beispiel den aktuellen Lux-Wert, den LED-Status und die Helligkeit.
Verbindung trennen und aufräumen¶
Die App kann einzelne BLE-Verbindungen oder alle aktiven Verbindungen trennen. Beim Trennen werden die laufenden Notify-Subscriptions beendet, die BLE-Verbindung wird geschlossen und die internen Zustände der App werden bereinigt.
Dieses Aufräumen ist wichtig, damit keine veralteten Verbindungen oder Listener bestehen bleiben. Dadurch bleibt die App stabil, auch wenn Geräte getrennt, neu verbunden oder zwischen verschiedenen Ansichten gewechselt wird.
Gateway-Mode¶
Hat ein Gerät selbst keinen Internetzugang, kann das Smartphone als Brücke zum Backend fungieren. Die App ist dann per BLE mit dem Gerät verbunden und besitzt über Mobilfunk oder WLAN einen eigenen Internetzugang. Im Gateway-Mode verbindet sie sich stellvertretend für das Gerät mit dem MQTT-Broker und leitet die Nachrichten in beide Richtungen weiter.
Die Weiterleitung läuft über die Geräte-Topics unter der MAC-Adresse des Geräts:
- Befehle vom Backend (
devices/<mac>/command) schreibt die App per BLE an das Gerät und bestätigt sie aufdevices/<mac>/ack. - Telemetrie, die das Gerät per BLE sendet, veröffentlicht die App auf
devices/<mac>/telemetry. - Zusätzlich meldet sie den Online-/Offline-Status des Geräts auf
devices/<mac>/status.
Für das Backend verhält sich das Gerät dadurch wie ein normal verbundenes MQTT-Gerät.
Voraussetzung
Die Brücke besteht nur, solange die App per BLE mit dem Gerät verbunden und selbst online ist. Sie wird je Gerät aktiviert und endet, sobald der Gateway-Mode beendet oder die Verbindung getrennt wird.