Digitalisierung, IoT und Sensordaten sind zur Zeit in aller Munde. Daher möchte ich in diesem Beitrag zeigen, wie Sie einen eigenen kleinen Sensor erstellen und dessen Daten an Power BI senden.
Die Komponenten für den Sensor sind recht günstig. Eine WeMos D1 mini bekommen Sie schon für unter 7€ und das Ultraschall Modul US-100 für unter 4€.
Natürlich können Sie auch jedes andere ESP8266 / ESP32 Board oder Ultraschall Modul (z.B. HC-SR04) verwenden. Das Ultraschall Modul US-100 hat jedoch den Vorteil, dass es auch mit 3,3V betrieben werden kann und über einen Temperatursensor verfügt.
Power BI Streamingdataset erstellen
Als Erstes müssen wir in Power BI einen Endpunkt für unsere Sensordaten erstellen. Hierfür erstellen Sie in Ihrem Arbeitsbereich ein Streamingdataset.
Als Quelle wählen Sie API aus und klicken auf Weiter.
Im nächsten Schritt benennen Sie das Streamingdataset und definieren die Datenstruktur. In diesem Beispiel erstellen wir eine Spalte “DateTime” vom Datentyp “DateTime”, eine Spalte “Distance” vom Datentyp “Zahl” und eine Spalte “Temprature” vom Datentyp “Zahl”.
Nachdem Sie Erstellen ausgewählt haben, wird das Streamingdataset erstellt. Im folge Dialog erhalten Sie die Push-URL, über die Sie Daten an den Endpunkt senden können. Kopieren Sie die URL für die spätere Verwendung.
Zusammenbau des Sensors
Die Verbindung vom US-100 Ultraschall Modul und dem WeMos D1 mini erfolgt wie folgt:
VCC - 3,3 / 5V
GND - GND
D1 - ECHO
D2 - TRIG
In der Realität sollte es dann wie folgt aussehen.
Anschließend konfigurieren wir das folgende Adruino Sketch mit SSID, PASSWORD und POWER BI API PUSH-URL und laden es auf dem WeMos D1 mini hoch.
#include <SoftwareSerial.h>;
#include <NTPClient.h>
#include <WiFiUdp.h>
#include <ESP8266WiFi.h>
#include <ESP8266WiFiMulti.h>
#include <ESP8266HTTPClient.h>
#include <WiFiClientSecureBearSSL.h>
// Fingerprint Power BI Certificate
const uint8_t fingerprint[20] = {0x23, 0x05, 0x3d, 0x63, 0x7d, 0x4c, 0x86, 0x66, 0x84, 0x17, 0x47, 0xe6, 0x37, 0x6b, 0xed, 0xbb, 0x23, 0x0b, 0x8d, 0xac};
WiFiUDP ntpUDP;
NTPClient timeClient(ntpUDP, "pool.ntp.org", 0, 3600000);
/**********************
* SET WIFI CREDENTIALS
**********************/
const char* ssid = "<SSID>";
const char* password = "<PASSWORD>";
/***************************
* SET Power BI API Push-URL
***************************/
const String pushURL = "<POWER BI API PUSH-URL>";
// defines pins numbers
const int US100_TX = 4;
const int US100_RX = 5;
SoftwareSerial US100Serial(US100_RX, US100_TX);
unsigned int MSByteDist = 0;
unsigned int LSByteDist = 0;
unsigned int mmDist = 0;
int temp = 0;
String formattedDate;
String jsonString;
void setup() {
Serial.begin(9600);
US100Serial.begin(9600);
Serial.print("Connecting to ");
Serial.println(ssid);
WiFi.begin(ssid, password);
while(WiFi.status() != WL_CONNECTED) {
delay(500);
Serial.print(".");
}
Serial.println("");
Serial.println("WiFi connected.");
Serial.println("IP address: ");
Serial.println(WiFi.localIP());
Serial.println("Start time client...");
timeClient.begin();
timeClient.update();
}
void loop() {
US100Serial.flush();
US100Serial.write(0x55);
delay(500);
if(US100Serial.available() >= 2)
{
MSByteDist = US100Serial.read();
LSByteDist = US100Serial.read();
mmDist = MSByteDist * 256 + LSByteDist;
if((mmDist > 1) && (mmDist < 10000))
{
Serial.print("Distance: ");
Serial.print(mmDist, DEC);
Serial.println(" mm");
}
}
US100Serial.flush();
US100Serial.write(0x50);
delay(500);
if(US100Serial.available() >= 1)
{
temp = US100Serial.read();
if((temp > 1) && (temp < 130)) // temprature is in range
{
temp -= 45; // correct 45º offset
Serial.print("Temp: ");
Serial.print(temp, DEC);
Serial.println(" ºC.");
}
}
timeClient.update();
formattedDate = timeClient.getFormattedDate();
Serial.print("DateTime: ");
Serial.println(formattedDate);
jsonString = "[{"DateTime": "" + formattedDate + "", "Distance": " + String(mmDist) + ", "Temprature": " + String(temp) + "}]";
Serial.print("Json: ");
Serial.println(jsonString);
Serial.println();
std::unique_ptr<BearSSL::WiFiClientSecure>client(new BearSSL::WiFiClientSecure);
client->setFingerprint(fingerprint);
HTTPClient https;
Serial.print("[HTTPS] begin...n");
// configure traged server and url
https.begin(*client, pushURL);
https.addHeader("Content-Type", "application/json");
Serial.print("[HTTPS] POST...n");
// start connection and send HTTP header
int httpCode = https.POST(jsonString);
// httpCode will be negative on error
if (httpCode > 0) {
// HTTP header has been send and Server response header has been handled
Serial.printf("[HTTPS] POST... code: %dn", httpCode);
// file found at server
if (httpCode == HTTP_CODE_OK) {
String payload = https.getString();
Serial.println(payload);
}
} else {
Serial.printf("[HTTPS] POST... failed, error: %sn", https.errorToString(httpCode).c_str());
String payload = https.getString();
Serial.println(payload);
}
https.end();
delay(9000);
}
Den “Fingerprint” des Power BI API Zertifikates können Sie über das Schlosssymbol in der Browserleiste auslesen.
In der Adruino Boardverwaltung habe ich das Paket esp8266 in der Version 2.5.0 geladen, da ich in den neueren Versionen Probleme mit der SoftwareSerial Bibliothek habe.
Als NTP Client nutze ich die angepasste Bibliothek “NTP Client library forked by Taranais“. Diese stellt eine Funktion getFormattedDate() bereit, die für die Übermittlung des Wertes DateTime genutzt wird.
Erstellung Sensor Dashboard
Zurück im Power BI Service fügen Sie in einem neuen Dashboard eine neue Kachel hinzu.
Als Quelle für die Kachel wählen Sie Benutzerdefinierte Streamingdaten.
Wählen Sie Ihr Streamingdataset aus.
Wählen Sie den Visualisierungstyp für Ihre Streamingdaten.
Abschließend können Sie noch weitere Kacheldetails definieren.
Jetzt sollten Sie sehen, wie Ihre Daten in Power BI gestreamt werden.
Lesen Sie auch:
Streaming von Daten aus dem SQL Server nach Power BI