Datenausgabe mit web2py

Seit einigen Tagen läuft die Datenerfassung der bisher experimentell verbauten Temperatursensoren (DS18S20) non-stop. Zeit genug sich Gedanken um die Ausgabe der Daten zu machen. Um nicht das Rad zum 100sten Mal zu erfinden stand von Anfang an fest, dass ich keine HTML-Ausgaben programmieren werde. Daher wurde ja bereits web2py installiert. Jetzt kommt es zum Einsatz.

Vorab muss ich feststellen, dass ich bisher keinerlei Erfahrungen mit web2py hatte, somit bei absolut Null angefangen habe. Große Hilfe an dieser Stelle ist die Dokumentation zu web2py, besonders der Teil „The Core“. Hinderlich, zumindest für mich, bei der web2py-Entwicklung war und ist, dass ich keine gewohnte IDE (Eclipse) und keine gewohnten Tools (wie Breakpoints, Variablen-Inspektor etc.) nutzen kann. Sehr viel funktioniert also anhand der bei Fehlern angezeigten web2py-Tickets und der darin gezeigten Fehlermeldungen.

web2py_v01

Das derzeitige Ergebnis der Ausgabe ist in der Grafik links zu sehen. Beim ersten Aufruf der Seite werden die vorhandenen Sensoren aufgelistet. Liegt in der Mappingtabelle ein zugeordneter Name vor, so wird dieser angezeigt.

Mit einem Klick auf einen der Sensoren werden die Daten aus der Datendatei geladen und unterhalb der Sensorenliste angezeigt.

In einer späteren Version wird es die Option geben die Daten als Tabelle (wie jetzt) anzeigen zu lassen oder als Diagramm.

Überblick

An der eigentlichen Datenerfassung und Speicherung in einer Textdatei pro Sensor (wie hier beschrieben) hat sich nichts geändert. An dieser Stelle geht es ausschließlich um die Ausgabe der Daten. Eine neue Datei ist in dem Verzeichnis in dem auch die Datendateien liegen dazugekommen. Da ich im Webinterface gerne verständliche Namen für die Sensoren sehen möchte enthält die Datei „sensor_mapping.txt“ eine Zuordnung der Datendatei zum gewünschten Namen.

Die Dateien von web2py liegen in meiner Installation unter „/home/www-data/web2py/“, die konkrete App somit unter „/home/www-data/web2py/applications/raspi/“.

Projekt zum Download: web2py.app.raspi

Das Projekt entält die folgenden relevanten (weil geänderten oder angelegten Dateien):

  • views/index.html
  • views/show_sensor_data.html
  • controllers/default.py

Der Controller nimmt die eigentliche Verarbeitung vor, während die Views nur für die Anzeige zuständig sind.

Controller/default.py

Der controller/default.py definiert die Funktionen die aufgerufen werden, wenn kein bestimmter Controller angegeben wird und ist daher der Einfachheit halber das Mittel der Wahl. Die Funktion index() wird immer aufgerufen, wenn keine spezielle Aktion aufgerufen wird. Diese Funktion wird also dafür zuständig sein die Liste der Sensoren anzuzeigen. Die Funktion show_sensor_data() ist für die Anzeige der Daten des ausgewählten Sensors verantwortlich. Die im selben Controller definierte Funktion test() ist genau dafür gedacht: Für Tests.

Funktion index()

Da diese Funktion die Liste der verfügbaren Sensoren anzeigen wird liest sie einfach die Mappingdatei sensor_mapping.txt an und formt aus deren Inhalt entsprechende Links. Das führt (beabsichtigt) dazu, dass nur die Sensoren angezeigt werden für die auch ein Name hinterlegt ist. Vorteil ist, dass sich so steuern lässt welche Sensoren angezeigt werden, so ggf. weitere Sensoren existieren die derzeit aber nicht berücksichtigt werden sollen.

Die Funktion index() ist wie folgt definiert:

Zeilenweise Beschreibung:

  • Zeile 2 und 3: Definition einer Pfad- und einer Dateikonstante
  • Zeile 4: Öffnen der Mappingdatei
  • Zeile 5: Lesen des Inhalts und Umwandeln in eine Liste (Ein Listeneintrag pro Zeile
  • Zeile 6: Schliessen der Mappingdatei
  • Zeile 7: Transformieren der Zeilen in ein Dict. Durch das „if len(_map) > 0“ werden Leerzeilen von der Umwandlung ausgeschlossen
  • Zeile 8: Rückgabe eines dicts und damit impliziter Aufruf der View index.html

 Funktion show_sensor_data()

Die Funktion läd die Datendatei des Sensors, kürzt die Daten auf die letzten 40 Zeilen, sortiert die Daten so dass der neueste Eintrag obensteht. Dann wird jede Zeile in Datum, Uhrzeit und Meßwert aufgespalten und somit aus der Liste eine Liste von Listen erzeugt. Letztendlich wird der Liste noch ein Headereintrag vorangestellt und zur Ausgabe an die View übergeben.

Und nun wieder zeilenweise:

  • Zeile 2: Definition des Pfades zur Datendatei
  • Zeile 3: Extrahieren des Namens der Dateidatei aus dem Request
  • Zeile 4: Extrahieren des Namens des Sensornamens aus dem Request
  • Zeile 5: Öffnen der Datendatei des Sensors
  • Zeile 6: Lesen des Inhalts
  • Zeile 7: Schließen der Datei
  • Zeile 8: Eingelesene Daten in eine Liste wandeln
  • Zeile 9: Die Liste auf die letzten 40 Einträge verkürzen und den letzten Eintrag wegwerfen (Leerzeile)
  • Zeile 10: Sortierung der Liste umkehren, da der neueste Eintrag oben stehen soll
  • Zeile 11: Definiton einer temporären Liste
  • Zeile 12: Öffnen des Loops durch die Liste
  • Zeile 13: Aufteilen der einzelnen Zeile in Datu, Zeit, Temperatur
  • Zeile 14: Wandeln der Temperatur in einen float und runden der Temperatur auf zwei Nachkommastellen
  • Zeile 15: Anfügen des neuen Listeneintrages an die temporäre Liste
  • Zeile 16: Einfügen der Datenbeschreibungen als ersten Eintrag der Liste
  • Zeile 17: Übergeben der Daten an die View show_sensor_daten.html

An dieser Stelle ist der wirklich programmtechnische Teil bereits erledigt, alles weitere ist Ausgabe der Daten in den beiden Views.

View index.html

Die View index.html kommt implizit zweimal zum Einsatz und ist ansich die View die immer sichtbar ist. Zum Ersten wird die View aufgerufen, wenn die Anwendung das erste Mal aufgerufen wird und die verfügbaren Sensoren angezeigt werden. Das zweite Mal kommt sie zum Einsatz, wenn ein Sensor ausgewählt wurde, da die Ausgaben der View show_sensor_data.html an der Stelle der View index.html ausgegeben wird die durch „<DIV id=sensors>“ definiert ist. Dass die Daten an dieser Stelle ausgegeben wird ist duch den Parameter target=“sensors“ im Aufruf von =A() festgelegt.

View show_sensor_daten.html

Die Ausgabe der Sensordaten ist letztendlich ein Zweizeiler, da die Vorarbeit bereits im Controller geleistet wurde. Die Aktion „show_sensor_data()“ übergibt eine Liste der Temperaturdaten des Sensors und den Namen des Sensors an die View, welcher mit {{=sensor_name}} in der Überschrift ausgegeben wird. Die Temperaturdaten müssten in einer Schleife ausgegeben werden, was allerdings freundlicher Weise der Helper =TABLE übernimmt, sodass diesem einfach die Liste der Daten übergeben werden kann. Im Ergebnis entsteht eine korrekt formatierte Tabelle an der Stelle die durch das „<DIV id=sensors>“ gekennzeichnet ist.

Abschluss

Wurden alle Dateien korrekt eingegeben oder an die richtige Stelle kopiert kann die Anwendung sofort aufgerufen werden. Die Auswahl eines Sensors führt dann zu einer Ausgabe wie sie im Bild am Anfang des Artikels gezeigt.

Ersten Kommentar schreiben

Antworten

Deine E-Mail-Adresse wird nicht veröffentlicht.


*


eins × 3 =