Übersicht Shelly BLU - Grundlagen und Gateway-Script

Die Shelly BLU Geräte sind batteriebetriebene Sensoren und Taster mit Bluetooth. Im Unterschied zu den übrigen Shelly Geräten haben sie kein WLAN und können deshalb auch keine MQTT Nachrichten senden. Sie funken ihre Messwerte als Bluetooth-Rundruf (Advertisement) im Format BTHome v2 in die Umgebung. Damit die Steuerung diese Werte erhält, wird ein Gateway benötigt: ein netzbetriebenes Shelly Gerät mit WLAN, das den Bluetooth-Rundruf empfängt und als MQTT Nachricht an die Steuerung weitergibt. Die Dekodierung der BTHome-Telegramme übernimmt die Steuerung selbst - das Script auf dem Gateway leitet die Rohdaten nur weiter. Neue Gerätetypen kommen daher mit einem Software-Update der Steuerung hinzu, ohne dass das Script geändert werden muss.

Diese Seite beschreibt, wie das Gateway eingerichtet wird, wie die Nachrichten aufgebaut sind und welches Script dafür auf dem Gateway läuft. Die Beschreibung der einzelnen Funktionsbausteine steht auf den jeweiligen Seiten der Geräte.

Gateway einrichten

  1. Ein Shelly Gerät der zweiten oder einer neueren Generation (Plus, Pro, Gen 3, Gen 4) in Empfangsreichweite der BLU Geräte montieren. Das Gerät muss dauerhaft mit Strom versorgt sein.
  2. Im Webinterface des Gerätes unter Bluetooth die Funktion Bluetooth Gateway einschalten.
  3. Unter MQTT die Verbindung zur Steuerung eintragen. Das Vorgehen ist auf der Seite MQTT Geräte - Allgemein beschrieben.
  4. Unter Scripts ein neues Script anlegen, das unten stehende Beispielscript einfügen, speichern und starten.
  5. Beim Script Autostart aktivieren, damit es nach einem Stromausfall selbständig wieder läuft.
  6. In der MQTT Diagnose der Steuerung prüfen, ob Nachrichten ankommen. Das dort angezeigte Topic wird beim jeweiligen Funktionsbaustein in den Parameter MQTT Topic eingetragen.
Ein Gateway kann mehrere BLU Geräte gleichzeitig weiterleiten. Bei größeren Gebäuden können auch mehrere Gateways eingesetzt werden; dann kann dasselbe Gerät von zwei Gateways gemeldet werden, was für die Auswertung unproblematisch ist.
Update-Hinweis: Das unten stehende Script setzt eine Steuerung ab Version 2.3131 voraus. Beim Umstieg gilt die Reihenfolge: zuerst die Steuerung aktualisieren, danach das Script tauschen - sonst kommen keine Werte an. Das bisherige große Script mit eingebauter Dekodierung funktioniert unverändert weiter, ein Tausch ist nicht zwingend. Werden mehrere Gateways eingesetzt, sollten alle mit demselben Script-Stand betrieben werden.
Ausnahme Ventilsteuerung: Der Shelly BLU TRV benötigt kein Script. Er wird mit dem Shelly BLU Gateway gekoppelt und über dessen eigene Nachrichten gesteuert und gelesen. Für das TRV wird im Baustein deshalb das Topic des Gateways und die Bluetooth ID des Ventils angegeben.

Aufbau der Nachrichten

Das Script veröffentlicht für jedes empfangene BLU Gerät eine Nachricht. Das Topic besteht aus dem im Script eingestellten Präfix und der Bluetooth-Adresse des Gerätes:

shelly-blu-aa:bb:cc:dd:ee:ff

Der Inhalt ist ein kleines JSON-Objekt mit den unveränderten Bluetooth-Nutzdaten in hexadezimaler Schreibweise:

{"sv":1,"addr":"aa:bb:cc:dd:ee:ff","rssi":-62,"sd":"40004201642e2f45d600"}

Dabei ist sv die Version des Nachrichtenformats, addr die Bluetooth-Adresse, rssi die Empfangsstärke und sd das BTHome-Telegramm. Die Steuerung dekodiert daraus die eigentlichen Werte, zum Beispiel:

{"encryption":false,"BTHome_version":2,"pid":66,"Battery":100,"humidity":47,"temperature":21.4,"addr":"aa:bb:cc:dd:ee:ff","rssi":-62}

In der MQTT Diagnose erscheinen beide Nachrichten untereinander: zuerst die Rohnachricht des Gateways, direkt danach die dekodierte Fassung mit den Feldnamen. Nachrichten des bisherigen großen Scripts kommen bereits dekodiert an und werden unverändert ausgewertet.

Wichtig: Das Topic darf keinen Schrägstrich enthalten. Die Steuerung wertet BLU Nachrichten nur aus, wenn das Topic aus einem einzigen Abschnitt besteht. Das voreingestellte Präfix shelly-blu- erfüllt diese Bedingung. Wird es geändert, müssen weiterhin Bindestriche statt Schrägstrichen verwendet werden.

Das Topic wird im Funktionsbaustein vollständig eingetragen, also einschließlich Präfix und Adresse. Am einfachsten wird es aus der MQTT Diagnose kopiert.

Welcher Wert landet auf welchem Ausgang

Werte im JSON

Kennung Feld im JSON Verwendung
0x01 Battery Batterie in Prozent. Alle BLU Bausteine geben den Wert am Ausgang "Batterie %" aus und setzen zusätzlich "Batterie Alarm", sobald der Wert 10 % oder weniger beträgt.
0x3a Button Tastendruck. Siehe Abschnitt "Besonderheit Taster".
0x2d Window Fensterkontakt, wird beim Baustein Door/Window am Ausgang "Fenster" ausgegeben.
0x3f Rotation Neigung des Door/Window Sensors in Grad.
0x21 motion Bewegung, wird beim Baustein Motion am Ausgang "Bewegung" ausgegeben. Kleingeschrieben.
0x05 Illuminance Helligkeit in Lux. Wird von Door/Window und Motion direkt ausgegeben. Bei der Wetterstation werden daraus zusätzlich Helligkeit in kLux, Dämmerung und Globalstrahlung berechnet.
0x45 temperature Temperatur in °C für H&T und Wetterstation. Kleingeschrieben.
0x2e humidity Relative Feuchte in Prozent für H&T und Wetterstation. Kleingeschrieben.
0x04 Pressure Luftdruck in hPa, Wetterstation.
0x08 Dewpoint Taupunkt in °C, Wetterstation.
0x44 Wind / Gust Windgeschwindigkeit in m/s. Die Wetterstation sendet Wind und Böe unter derselben Kennung. Bei der Dekodierung werden beide Werte aufgetrennt: der erste Wert wird zu "Wind", der zweite zu "Gust".
0x5e WindDir Windrichtung in Grad, Wetterstation.
0x46 UV UV-Index, Wetterstation.
0x20 Raining Regen ja/nein. Dieser Binärwert reagiert schneller als der Millimeterzähler. Ältere Scriptstände melden ihn unter dem Namen "Moisture", beide Schreibweisen werden gelesen.
0x5f Rain Regenzähler in mm. Aus dem fortlaufenden Zählerstand berechnet die Steuerung Regenrate, Ereignis, Stunde, Tag, Woche, Monat, Jahr und Gesamtmenge.
0x0c
0x4a
Voltage Spannung. Bei der Wetterstation die Spannung des Superkondensators.
Groß- und Kleinschreibung: Die Feldnamen erzeugt die Steuerung bei der Dekodierung selbst, ihre Schreibweise ist damit fest vorgegeben. Nur beim bisherigen großen Script, das die Werte selbst dekodiert, ist auf zeichengenaue Feldnamen zu achten: "Battery" wird groß geschrieben, "temperature", "humidity" und "motion" dagegen klein - sonst bleiben die Ausgänge auf ihrem alten Wert stehen.

Besonderheit Taster

Beim Shelly BLU Button 1 enthält das Feld "Button" eine einzelne Zahl. Sie gibt an, wie oft beziehungsweise wie lange gedrückt wurde:
  • 1 = einmal kurz
  • 2 = zweimal
  • 3 = dreimal
  • 4 = lang
Beim Shelly BLU RC Button 4 enthält das Feld "Button" stattdessen eine Liste mit vier Werten, je einen für jede Taste. Der Wert 254 bedeutet, dass diese Taste gedrückt wurde:

"Button":[0,0,254,0]

Diese Liste entsteht, weil bei der Dekodierung mehrfach vorkommende Kennungen gesammelt statt überschrieben werden.

Aufbau des Scripts

CONFIG Einstellungen. In topic_prefix steht das Topic-Präfix (ohne Schrägstrich). Mit address kann auf ein einzelnes Gerät eingeschränkt werden; im Auslieferungszustand werden alle empfangenen Geräte weitergeleitet.
toHex Wandelt die Bluetooth-Nutzdaten in hexadezimale Schreibweise für den MQTT-Versand um.
last_pid Unterdrückt Wiederholungen. Die Paketnummer wird je Geräteadresse gemerkt, damit sich mehrere BLU Geräte nicht gegenseitig ausblenden. Geräte ohne Paketnummer, etwa die Wetterstation, und verschlüsselte Telegramme werden nicht unterdrückt.
scanCB Wird bei jedem empfangenen Bluetooth-Rundruf aufgerufen, filtert BTHome-Telegramme (Service-Kennung fcd2) heraus und veröffentlicht die Rohdaten über MQTT.

Beispielscript

Das Script leitet die Rohdaten aller BTHome-Geräte in Empfangsreichweite weiter. Welche Gerätetypen ausgewertet werden, bestimmt die Steuerung - derzeit: Button 1, RC Button 4, Door/Window, Motion, H&T und die Wetterstation Ecowitt WS90. Neue Gerätetypen kommen mit einem Software-Update der Steuerung hinzu, das Script bleibt dabei unverändert.

// Shelly BLU Gateway - Minimalversion
// Leitet die BTHome-Rohdaten der Shelly BLU Geraete per MQTT an die Steuerung
// weiter. Die Dekodierung der Telegramme uebernimmt die Steuerung (ab Version
// 2.3131) - neue Geraetetypen erfordern daher kein Script-Update mehr.

let CONFIG = {
  topic_prefix: "shelly-blu-",      // kein "/" verwenden!
  // address: "aa:bb:cc:dd:ee:ff", // optional: nur dieses Geraet weiterleiten
};

let HEX = "0123456789abcdef";
function toHex(s) {
  let out = "";
  for (let i = 0; i < s.length; i++) {
    let hi = (s.at(i) >> 4) & 0x0f;
    let lo = s.at(i) & 0x0f;
    out = out + HEX.slice(hi, hi + 1) + HEX.slice(lo, lo + 1);
  }
  return out;
}

let last_pid = {};
function scanCB(ev, res) {
  if (ev !== BLE.Scanner.SCAN_RESULT) return;
  // nur BTHome-Telegramme (Service-Kennung fcd2) weiterleiten
  if (typeof res.service_data === "undefined" || typeof res.service_data["fcd2"] === "undefined")
    return;
  if (typeof CONFIG.address !== "undefined" && CONFIG.address !== res.addr)
    return;
  let sd = res.service_data["fcd2"];
  if (sd.length < 1) return;
  // Wiederholungen unterdruecken: die Paketnummer (Kennung 0x00) steht laut
  // BTHome-Spezifikation immer als erstes Objekt nach dem Info-Byte.
  // Verschluesselte Telegramme und Geraete ohne Paketnummer (z.B. die
  // Wetterstation WS90) werden nicht unterdrueckt.
  if ((sd.at(0) & 1) === 0 && sd.length >= 3 && sd.at(1) === 0) {
    if (last_pid[res.addr] === sd.at(2)) return;
    last_pid[res.addr] = sd.at(2);
  }
  let msg = '{"sv":1,"addr":"' + res.addr + '","rssi":' + JSON.stringify(res.rssi) + ',"sd":"' + toHex(sd) + '"}';
  if (MQTT.isConnected() === false) {
    console.log("MQTT not connected");
    return;
  }
  if (MQTT.publish(CONFIG.topic_prefix + res.addr, msg, 0, false) === false)
    console.log("MQTT error publish");
}
console.log("BLE.Scanner.Start");
BLE.Scanner.Start({ duration_ms: BLE.Scanner.INFINITE_SCAN, active: false }, scanCB);

Siehe auch MQTT Geräte - Allgemein.
Siehe auch allgemeine Parameter aller Funktionsbausteine.