Bildbasierte Detektion eines Garagentores

 

Einleitung

Unser elektrisches Garagentor schließt nicht selbständig. Da wir den Tor-Öffner nicht ersetzen wollen, wollten wir das automatische Schließen im Eigenbau nachrüsten oder zumindest eine Möglichkeit schaffen, um an das Schließen des Tores erinnert zu werden. Die Umsetzung sollte über ein optisches Verfahren geschehen, auch wenn das bei weitem nicht der einfachste Weg ist, um zu erkennen, ob das Garagentor offen oder geschlossen ist. Als zusätzlicher Anreiz wurde versucht, möglichst viel Funktionalität mit dem Azure Technologie Stack zu erledigen. Gedanke dahinter war, sich mit den Möglichkeiten und derzeitigen Einschränkungen von Azure vertraut zu machen.

Aufbau

Um einen Detektor trainieren zu können benötigen wir gelabelte Trainingsdaten. Da wir aktuell noch nicht über die nötigen Daten verfügen, befasst sich dieser Post vornehmlich mit der Datenakquise. Im kommenden Post werden wir die Daten aufbereiten und ein geeignetes maschinelles Lernverfahren suchen um eine Detektion durchführen zu können.

Für die Beschaffung der Trainingsdaten wird ein Raspberry Pi 3 Model B (Pi3) verwendet, der in regelmäßigen Abständen über eine angeschlossene PiCamera ein Bild aufnimmt und an einen Web-Server sendet. Der Server wiederum legt das Bild im Azure Blob Storage (AzureBlobStorage) ab und erstellt eine Datei mit Zeitstempel die in Azure DocumentDB (AzureDocumentDB) abgelegt wird. Dieser Aufbau ist schematisch auch in Grafik 1:Aufbau dargestellt.

 

Grafik 1: Exemplarischer Aufbau. Eingebettete Grafiken stammen von OpenClipArts: http://openclipart.org

Implementierung

Für die Datenakquise sind zwei kleinere Anwendungen verantwortlich. Die erste Anwendung läuft auf dem Raspberry PI 3, die in regelmäßigen Abständen ein Bild aufnimmt und es an die zweite Anwendung übermittelt.

Bei der zweiten Anwendung handelt es sich um eine kleine Web API die mittels Flask implementiert wurde. Ihre Aufgabe ist es, das Bild im Azure Blob Storage zu speichern, sowie einen Eintrag in Azure DocumentDB hinzuzufügen, damit wir später dem Bild einen Status zuordnen können.

Die folgenden zwei Unterkapitel gehen ausführlicher auf die Implementierung der beiden Anwendungen ein.

Implementierung Raspberry Pi

Auf dem Raspberry Pi wurde zunächst Rasbian mit Hilfe von NOOBS installiert. Auch die Installation der PiCamera erfolgte zunächst anhand der unter PiCamera zu findenden Anleitung. Die Implementierung weicht dann verständlicherweise vom Beispielcode ab, um den Upload zum Server bewerkstelligen zu können.

In regelmäßigen Abständen (derzeit alle \60\) Sekunden) wird ein Foto erstellt und mit aktuellem Zeitstempel als Dateinamen gespeichert:

Das gespeicherte Bild wird anschließend an den Server übermittelt:

Damit ist die Aufgabe des Pi bereits erledigt. Die Persistierung übernimmt das Backend.

Server

Beim Backend handelt es sich um eine auf Azure gehostete Web App, die mithilfe von Flask realisiert wurde. Die Erstellung der Web App erfolgte über den bei Azure vorhanden Assistenten. Folgende Schritte im Azure Portal waren nötig, um die Web App zu erstellen:

  1. New Button betätigen
  2. In der Suchmaske nach Flask suchen
  3. Flask PTVS auswählen und den Wizard abschließen

Anschließend wurde das Deployment über einen git remote eingerichtet:

  1. In der erstellten Web App Deployment Options auswählen
  2. Die vorhanden Deployment Option mittels Disconnect auflösen 1
  3. Über Setup → Choose Source → Local Git Repository kann man
    anschließend das Deployment per lokalem Git Repository ermöglichen 2
  4. Die URL zum Klonen ist anschließend unter dem Reiter Overview in der Web App zu finden. Dadurch kann man den Quellcode auf den PC klonen.

Eine ausführlichere Erläuterung der einzelnen Schritte ist unter FlaskAzureStartup zu finden.

Damit wäre die Web App erstellt und kann nun an unsere Anforderungen angepasst werden. Aktuell benötigen wir nur einen Post-Request der ein Bild entgegennimmt, es im Azure Blob Storage speichert und einen passenden Eintrag im Azure DocumentDB ablegt.

Um das Bild zu speichern nutzen wir AzureStoragePython. Dazu ergänzen wir die Datei requirements.txt um azure-storage<0.33.0. Wir nutzen ganz bewusst nicht die aktuellste Version, da es mit dieser Probleme beim Azure Deployment gibt. Um DocumentDB nutzen zu können, fügen wir zusätzlich pydocumentdb zur Datei hinzu. Zusätzlich löschen wir die Datei skipPythonDeployment da die Abhängigkeiten sonst nicht in unserer Web App installiert werden.

Damit wären die nötigen Abhängigkeiten installiert und wir können uns nun um den Post-Request kümmern. Nachfolgend der komplette Code zur Speicherung des Bildes und zur Erstellung des Eintrages, den wir im Fortgang des Kapitels näher erläutern:

Zunächst importieren wir die nötigen Objekte und Module. Anschließend erstellen wir mit dem Aufruf

einen BlockBlobService. Mit diesem können wir durch den Aufruf von

einen neuen Blob erstellen und das übertragene Bild darin ablegen.

Anschließend erstellen wir noch einen Eintrag im Azure DocumentDB. Diesen brauchen wir um später die Trainingsdaten labeln zu können. Der Eintrag enthält also ein flag open, das angibt, ob das Tor offen oder geschlossen ist. Der komplette Aufruf zur Erstellung des Eintrages ist wie folgt:

Zunächst instanziieren wir einen client. Die nächsten beiden Zeilen werden benötigt um die richtige Collection zu finden, in der der Eintrag erstellt werden soll. Die Erstellung wird letztendlich von der letzten Zeile des Listings erledigt.

Zusammenfassung

Die in diesem Artikel vorgestellte Implementierung generiert die für unsere Detektion nötigen Trainingsdaten und legt sie automatisiert im Azure Blob Storage und Azure DocumentDB ab. Da durch die aktuelle Implementierung täglich 1440 Bilder erstellt werden, sind wir gut gerüstet für das Training im folgenden Artikel. In diesem befassen wir uns mit dem Labeln der Daten und dem Finden eines geeigneten Klassifikators.

Anhang

Literaturverzeichnis

Fußnoten:

1

Das ursprüngliche Deployment ist noch vorhanden. Alternativ ist sie auch unter https://github.com/azureappserviceoss/FlaskAzure zu finden

2

Beim ersten Einrichten des Deployments via git muss zunächst ein Benutzer unter Deployment Credentials angelegt werden. Details dazu unter https://docs.microsoft.com/de-de/azure/app-service-web/app-service-deploy-local-git