Stromkosten als Diagramm darstellen

Schaltbare Steckdosen spielen in FHEM eine große Rolle. Einige von ihnen sind jedoch nicht nur zum einfachen Schalten da, sondern messen zusätzlich auch die aktuelle Leistung und den Stromverbrauch des angeschlossenen Gerätes. Ein Beispiel ist da die PCA301-Steckdose von ELV oder der Zwischenstecker von HomeMatic.

Letzte Aktualisierung am 23.08.2017 / Affiliate Links / Bilder von der Amazon Product Advertising API

Da liegt es doch Nahe, aus den gemessenen Werte sich den Stromverbrauch des angeschlossenen Gerätes zu errechnen und in einem Balkendiagram darzustellen. Genau darum wird es in diesem Blogbeitrag gehen. Ich werde euch zeigen, wir ihr die Readings einer PCA301-Steckdose auswertet und euch daraus ein Dummy mit den Tages-, Monats, Jahres- und Gesamtverbrauch und den jeweiligen Stromkosten erstellt.

Vorbereitung

Bevor man mit dem Auswerten der Readings beginnen kann, muss natürlich die Steckdose selbst eingebunden werden. Mehr Infos dazu auf meinem Blogbeitrag. Folgende Anweisungen beziehen sich auf die Readings der PCA301-Steckdosen. Solltet ihr andere Leistungsmessgeräte verwenden, müsst ihr die Readings entsprechend anpassen.

Einrichtung in FHEM

Der komplette Aufbau besteht aus je einem Dummy für die Gesamt-, Jahres-, Monats, und Tageswerte. Die Dummys besitzen dann je ein Reading für den Verbrauch und für die Stromkosten. Die Dummys für die Gesamt-, Jahren- und Monatswerte besitzen zudem ein Reading für den Tagesverbrauch. Aus diesem Reading wird dann entsprechend der Gesamt-, Jahres- bzw. Monatswert errechnet.

Das Reading Tagesverbrauch wird dann über ein at-Device mit dem gemessen Wert der Steckdose beschrieben. Die anderen Readings werden jeweils im Dummy über das userReadings-Attribut selbst erzeugt. 

Zusätzlich wird im at-Device das aktuelle Datum abgefragt, um zu überprüfen, ob eines der Readings zurückgesetzt werden muss. Am ersten Tag eines Monats wird zum Beispiel das Reading Verbrauch des Monats-Dummys auf Null gesetzt.

Zum Schluss wird noch eine readingsGroup erstellt, um die Werte in einem Device zusammen zu haben.

Dummys

Wie oben bereits erwähnt, wird je ein Dummy für die Gesamt-, Jahres-, Monats- und Tageswerte erstellt.

define WZStromkostenGesamt dummy
define WZStromkostenJahr dummy
define WZStromkostenMonat dummy
define WZStromkostenTag dummy

Damit die später eingerichteten Readings ordnungsgemäß verarbeitet und angezeigt werden, werden den Dummys ein paar Attribute mitgegeben. Angefangen mit dem Gesamt-Dummy.

Attribut "alias", damit der unschöne Name überschrieben wird:

attr WZStromkostenGesamt alias Gesamt

Attribut "room" für die Raumzuordnung:

attr WZStromkostenGesamt room Stromkosten

Mit dem Attribut "group" werden die Dummys zusammengefasst:

attr WZStromkostenGesamt group WZ-Stromkosten

Die Attribute "alias", "room" und "group" können natürlich je nach Wunsch angepasst werden.

Attribut "stateFormat" fügt die Readings in die Device-Übersicht:

attr WZStromkostenGesamt stateFormat {sprintf("%.2f kWh - %.2f €",
ReadingsVal("WZStromkostenGesamt", "Verbrauch",0),
ReadingsVal("WZStromkostenGesamt","Kosten",0))}

Attribut "userReadings" fügt das Reading "Verbrauch" hinzu, welches den Tageswert stetig aufaddiert und das Reading "Kosten", welches den Verbrauchswert mit dem aktuellen Strompreis multipliziert.

attr WZStromkostenGesamt userReadings Verbrauch monotonic 
{ReadingsVal("WZStromkostenGesamt","Tagesverbrauch",0)}, Kosten {ReadingsVal("WZStromkostenGesamt","Verbrauch",0)*0.2507}

Diese Attribute anschließend auch für die beiden Dummys "WZStromkostenJahr" und "WZStromkostenMonat" einrichten. Bei den Attributen "stateFormat" und "userReadings" entsprechend die Devices im ReadingsVal anpassen. 

Für das Dummy "WZStromkostenTag" können die Attribute "alias", "room" und "stateFormat" ebenfalls übernommen werden. Das Attribut "userReadings" wird jedoch etwas abgewandelt:

attr WZStromkostenTag userReadings Kosten {
ReadingsVal("WZStromkostenTag","Verbrauch",0)*0.2507}

Hier wird nur noch das Reading "Kosten" erstellt. Das Verbrauchs-Reading wird später über das at-Device erzeugt.

at-Device

Nachdem die Dummys erstellt wurden, kann man damit beginnen, diese mit Leben zu füllen. Verwendet wird dafür ein at-Device, welches zunächst wie folgt definiert wird:

define atWZStromkosten at +*00:01:00 a

Über den DEF-Editor passen wir das at-Device nun an:

+*00:01:00 {
my $a = (ReadingsVal("WZ_Entertainment","consumption",0));

fhem("setreading WZStromkostenTag Verbrauch $a");
fhem("setreading WZStromkostenMonat Tagesverbrauch $a");
fhem("setreading WZStromkostenJahr Tagesverbrauch $a");
fhem("setreading WZStromkostenGesamt Tagesverbrauch $a");

if(($hour==0) && ($min==0)){
fhem("set WZ_Entertainment reset")}

if(($hour==0) && ($min==0) && ($mday==1)){
fhem("setreading WZStromkostenMonat Verbrauch 0")}

if(($hour==0) && ($min==0) && ($yday==1)){
fhem("setreading WZStromkostenJahr Verbrauch 0")}
}

Nachtrag 01.03.2017: Heute zum 1. des Monats, habe ich festgestellt, dass das Zurücksetzen am Anfang des Monats nicht geklappt hat. Grund war der Einsatz von "elsif". Es wird dann nämlich nur die erste Bedienung ausgeführt (die Tageszurücksetzung). Die anderen Abfragen werden dann gar nicht mehr überprüft. Durch den Einsatz von drei getrennten if-Abfragen sollte es nun aber klappen. Der Code oben wurde bereits angepasst.

Zuerst wird die Variable "a" erzeugt, diese beinhaltet den gemessenen Stromverbrauch der PCA301-Steckdose. Solltet ihr hier andere Devices für die Messung verwenden, mit eventuell anderen Readings, müsst ihr diesen Eintrag entsprechend anpassen.

Anschließend wird das Reading "Verbrauch" vom Tages-Dummy mit diesem Wert gesetzt. Die anderen Dummys bekommen diesen Wert als Reading "Tagesverbrauch". Aus diesem Reading wird innerhalb der Dummys zum Beispiel der Jahresverbrauch erstellt, siehe Attribut "userReadings" der Dummys.

Nachdem die Readings gefüttert wurden, beginnt die Zeitabfrage. Zuerst wird nach der Uhrzeit "00:00" gefragt. Ist dies der Fall, wird die Verbrauchsmessung der PCA301-Steckdose ("WZ_Entertainment") auf Null gesetzt. Die zweite Abfrage überprüft, ob ein neuer Monat begonnen hat. In diesem Fall, wird der Monatsverbrauch auf Null gesetzt. Die letzte Abfrage ist für den Jahreswechsel zuständig. Bei einem Jahreswechsel wird das Jahresverbrauch entsprechend auf Null gesetzt.

Wurde das ordnungsgemäß at-Device eingerichtet, werden die Dummys nun mit den entsprechenden Werten gespeißt und die Berechnung des Monats-, Jahres- und Gesamtverbrauch beginnt.

Zu Beginn sieht es noch etwas unspektakulär aus, da es zwischen den Zeiträumen keinen Unterschied gibt. Aber das wird sich ja mit der Zeit ändern.

readingsGroup

Wer möchte, kann die Readings noch in einer "readingsGroup" zusammen fassen. Dies erleichtert zum Beispiel ein späteres Verschieben in einen anderen Raum, da nur noch für die "readingsGroup" das room-Attribut angepasst werden muss. Des Weiteren lässt sich diese Gruppe visuell besser anpassen als eine Gruppierung über das group-Attribut.

define GroupWZStromkosten readingsGroup < >,<Verbrauch>,<Kosten> 
WZStromkostenGesamt:Verbrauch,Kosten
WZStromkostenJahr:Verbrauch,Kosten
WZStromkostenMonat:Verbrauch,Kosten
WZStromkostenTag:Verbrauch,Kosten

Anstatt nun die ganzen Dummys in den Raum "Wohnzimmer" zu verschieben, muss ich nun nur diese Gruppe in den gewünschten Raum verschieben.

attr GroupWZStromkosten room Wohnzimmer

Auch hier setze ich wieder das alias-Attribut:

attr GroupWZStromkosten alias Stromkosten

Wer möchte kann gerne noch das Aussehen der Gruppe anpassen. Ich zum Beispiel habe die Schriftgröße auf 18px erhöht und Wertebereiche den Farben grün, orange und rot zugeordnet.

attr GroupWZStromkosten valueStyle {
if($DEVICE eq "WZStromkostenJahr" && $READING eq "Verbrauch" && $VALUE > 1800)
{'style="color:red"'} elsif($DEVICE eq "WZStromkostenJahr" && $READING eq "Verbrauch" && $VALUE > 1080)
{'style="color:orange"'} elsif($DEVICE eq "WZStromkostenJahr" && $READING eq "Verbrauch" && $VALUE > 0)
{'style="color:green"'} elsif($DEVICE eq "WZStromkostenJahr" && $READING eq "Kosten" && $VALUE > 460)
{'style="color:red"'} elsif($DEVICE eq "WZStromkostenJahr" && $READING eq "Kosten" && $VALUE > 275)
{'style="color:orange"'} elsif($DEVICE eq "WZStromkostenJahr" && $READING eq "Kosten" && $VALUE > 0)
{'style="color:green"'}
elsif($DEVICE eq "WZStromkostenMonat" && $READING eq "Verbrauch" && $VALUE > 150)
{'style="color:red"'} elsif($DEVICE eq "WZStromkostenMonat" && $READING eq "Verbrauch" && $VALUE > 90)
{'style="color:orange"'} elsif($DEVICE eq "WZStromkostenMonat" && $READING eq "Verbrauch" && $VALUE > 0)
{'style="color:green"'} elsif($DEVICE eq "WZStromkostenMonat" && $READING eq "Kosten" && $VALUE > 38)
{'style="color:red"'} elsif($DEVICE eq "WZStromkostenMonat" && $READING eq "Kosten" && $VALUE > 23)
{'style="color:orange"'} elsif($DEVICE eq "WZStromkostenMonat" && $READING eq "Kosten" && $VALUE > 0)
{'style="color:green"'}
elsif($DEVICE eq "WZStromkostenTag" && $READING eq "Verbrauch" && $VALUE > 5)
{'style="color:red"'} elsif($DEVICE eq "WZStromkostenTag" && $READING eq "Verbrauch" && $VALUE > 3)
{'style="color:orange"'} elsif($DEVICE eq "WZStromkostenTag" && $READING eq "Verbrauch" && $VALUE > 0)
{'style="color:green"'} elsif($DEVICE eq "WZStromkostenTag" && $READING eq "Kosten" && $VALUE > 1.25)
{'style="color:red"'} elsif($DEVICE eq "WZStromkostenTag" && $READING eq "Kosten" && $VALUE > 0.75)
{'style="color:orange"'} elsif($DEVICE eq "WZStromkostenTag" && $READING eq "Kosten" && $VALUE > 0)
{'style="color:green"'} }

Die Wertebereiche könnt ihr natürlich entsprechend anpassen.

attr GroupWZStromkosten style style="font-size:18px"

Zum Schluss wird noch das Format der Werte angepasst und die Einheit hinzugefügt.

attr GroupWZStromkosten valueFormat {Kosten => "%.2f €", Verbrauch => "%.2f kWh"}

FileLog

Damit später auch ein Diagramm erstellt werden kann, müssen die Werte in ein FileLog gespeichert werden. Ich habe mich für ein extra FileLog für die Stromkosten entschieden.

define StromkostenLOG FileLog ./log/StromkostenLOG-%Y-%m.log 
WZStromkostenGesamt:.*|WZStromkostenJahr:.*|WZStromkostenMonat:.*|WZStromkostenTag:.*

Wer möchte, kann natürlich die Werte auch in ein vorhandenes FileLog schreiben.

Für das Diagramm wird später der Kosten-Wert vom Dummy "WZStromkostenGesamt" verwendet. Dennoch schreibe ich auch die Tages-, Monats- und Jahreswerte in das LogFile. Dies erleichtert zum Beispiel, dass spätere Erstellen von einem Monatsdiagramm. Am Anfang ist dies jedoch aufgrund der geringen Anzahl an Werten nicht zu empfehlen.

Balkendiagramm

Nachdem das FileLog erstellt wurde, kann mit dem Definieren des Diagramms begonnen werden. Wie oben schon erwähnt, habe ich mir zuerst nur ein Diagramm aus den Tageswerten erstellt.

define SVGStromkosten SVG StromkostenLOG:SVG_StromkostenLOG:CURRENT

Das Erstellen des SVG-Plots geht natürlich auch über das LogFile und dann über "Create SVG Plot".

Bevor man nun das Diagramm weiter definiert, ist für eine korrekte Anzeige notwendig den Zeitraum auf einen Monat festzulegen.

attr SVGStromkosten fixedrange month

Optional kann noch die Größe des Diagramms, der Raum und ein Alias festgelegt werden. Ich verwende eine einheitliche Größe von 800x200 Pixel.

attr SVGStromkosten plotsize 800,200
attr SVGStromkosten room Wohnzimmer
attr SVGStromkosten alias Stromkosten

Um nun das gewünschte Balkendiagramm angezeigt zu bekommen, habe ich folgende Einstellungen vorgenommen. Wie oben schon erwähnt, verwende ich den Kosten-Werte vom Dummy "WZStromkostenGesamt".

Wichtig ist hier der Eintrag im Feld "functions". "delta-d" sorgt dafür, dass aus dem Gesamt-Kostenwert immer nur die Kosten des Tages angezeigt werden, bzw. die Differenz von den Gesamtkosten gegenüber des Wertes vom letzten Tag. Kurz gesagt, die anfallenden Kosten eines Tages.

Wer möchte, kann nun natürlich auch ein Diagramm für den täglichen Verbrauch in kWh erstellen. Oder anstelle von Tagesdiagrammen ein Stundendiagramm erstellen. Dazu einfach die Function "delta-d" zu "delta-h" ändern. Achtet jedoch darauf, dass für jedes Diagramm ein seperates FileLog benötigt wird.

Absofort wird von jedem Tag ein Balken mit den angefallenen täglichen Stromkosten des gemessenen Gerätes erstellt. Zusammen mit der readingsGroup hat man nun eine sehr gute Übersicht über die angefallenden Stromkosten.

Messdaten mehrerer Steckdosen zusammenfügen

Die oben beschriebene Anleitung beschreibt das Visualisieren von Messdaten eines Messgerätes. In diesem Fall eine PCA-301-Steckdose. Hat man jedoch mehrere Mess-Steckdosen im Einsatz, kann es nützlich sein, alle Messwerte zusammenzuführen und somit den Gesamtverbrauch aller Steckdosen anzeigen zu lassen.

In meinem Fall habe ich zuerst die oben beschriebenen Schritte auch für meine zweite PCA-310-Steckdose im Arbeitszimmer durchgefüht und besitze nun folgende Dummys:

  • WZStromkostenGesamt
  • WZStromkostenJahr
  • WZStromkostenMonat
  • WZStromkostenTag
  • AZStromkostenGesamt
  • AZStromkostenJahr
  • AZStromkostenMonat
  • AZStromkostenTag

Die neu hinzugekommenen Dummys (AZStromkostenGesamt ...) werden ebenfalls durch ein at-Device mit den Werten gefüttert und innerhalb der Dummys werden die Kosten berechnet. Mehr dazu in den oberen Schritten. Das Anlegen einer readingsGroup, FileLog und eines Diagramms sind optional und werden für folgende Schritte nicht unbedingt benötigt.

Für die Zusammenfassung der Messwert werden ebenfalls vier Dummys angelegt.

define StromkostenGesamt dummy
define StromkostenJahr dummy
define StromkostenMonat dummy
define StromkostenTag dummy

Auch diese Dummys bekommen wieder ein paar Attribute. Jeweils für die einzelnen Dummys entsprechend anpassen.

attr StromkostenGesamt alias Gesamt
attr StromkostenGesamt room Stromkosten
attr StromkostenGesamt group Gesamt-Stromkosten
attr StromkostenGesamt stateFormat {sprintf("%.2f kWh - %.2f €",
ReadingsVal("StromkostenGesamt", "Verbrauch",0),
ReadingsVal("StromkostenGesamt","Kosten",0))}

Im Gegensatz zu den Dummys für die einzelnen Geräte, muss bei den Gesamt-Dummys der Verbrauch nicht über "monotonic" errechnet werden. Hier erhalten alle Dummys den Verbrauchswert später über das at-Device, welches ja nur noch die einzelnen Werte zusammen zählen muss. Die Kosten könnte man auch über das at-Device zusammen zählen lassen, ich habe mich jedoch dafür entschieden, diese wieder im Dummy selber zu errechnen.

attr StromkostenGesamt userReadings Kosten {
ReadingsVal("StromkostenGesamt","Verbrauch",0)*0.2507}

Genau wie bei den beiden einzelnen Messgeräte (PCA301-Steckdose) werden für die Dummys des Gesamtverbrauches ebenfalls ein at-Device angelegt.

define atGesamtStromkosten at +*00:01:00 a

Über den DEF-Editor wird das at-Device nun mit Leben befüllt:

+*00:01:00 {
my $a = (ReadingsVal("WZStromkostenGesamt","Verbrauch",0));
my $b = (ReadingsVal("WZStromkostenJahr","Verbrauch",0));
my $c = (ReadingsVal("WZStromkostenMonat","Verbrauch",0));
my $d = (ReadingsVal("WZStromkostenTag","Verbrauch",0));
my $e = (ReadingsVal("AZStromkostenGesamt","Verbrauch",0));
my $f = (ReadingsVal("AZStromkostenJahr","Verbrauch",0));
my $g = (ReadingsVal("AZStromkostenMonat","Verbrauch",0));
my $h = (ReadingsVal("AZStromkostenTag","Verbrauch",0));

my $Gesamt = $a + $e;
my $Jahr = $b + $f;
my $Monat = $c + $g;
my $Tag = $d + $h;

fhem("setreading StromkostenGesamt Verbrauch $Gesamt");
fhem("setreading StromkostenJahr Verbrauch $Jahr");
fhem("setreading StromkostenMonat Verbrauch $Monat");
fhem("setreading StromkostenTag Verbrauch $Tag");
}

Das at-Device besorgt sich nun die Werte der beiden PCA301-Steckdosen und rechnet die jeweils zusammen. Anschließend übermittelt es die errechneten Werte an die vier Gesamt-Dummys.

Absofort werden die Messwerte (Gesamt, Jahr, Monat und Tag) der beiden Mess-Steckdosen zusammengerechnet und in in den erstellen Dummys übersichtlich dargestellt. Wer möchte kann natürlich auch von den Gesamt-Dummys eine readingsGroup oder ein Diagramm erstellen. Mehr Infos dazu, entnehmt ihr aus den vorangegangenen Schritten.

Mir ist zwar bewusst, dass es eine Menga zu definieren gibt. Das Ergebniss hat mich jedoch überzeugt. Ich habe somit einen guten Überblick über die angefallenen Stromkosten. Hat man nun zum Beispiel eine Mess-Steckdose über, so kann man diese ja als mobiles Messgerät definieren und somit Langzeittests von unterschiedichen Geräten durchführen. Stromfresser hat man dann schnell ermittelt. 

Ich hoffe ich konnte euch meine Idee der Stromkosten- und Verbrauchsanalyse etwas näher bringen. Solltet ihr Ideen haben, wie man dies eleganter reallisiert, könnt ihr gerne ein Kommentar hinterlassen. Ich bin für jede Idee dankbar.

Hinterlasse einen Kommentar

10 Kommentare auf "Stromkosten als Diagramm darstellen"

Benachrichtige mich zu:
avatar
Fotos und Bilder
 
 
 
sonstiges Dateiformat
 
 
 
Sortiert nach:   neuste | älteste | beste Bewertung
Sascha
Gast
Sascha

Hallo.

 

Ich habe mir deinen Blog durchgelesen und soweit auch umgesetzt.

Jedoch habe ich ein Problem. Ich habe eine Revolt Messsteckdose die folgende Daten funkt (siehe unten)

energy ist der bis dato gesamt gemessene Verbrauch. power der Momentane Verbrauch.

Welchen von den beiden readings soll verwendet werden ?

Ich habe erstmal energy benutzt. Da passt dann aber der Tagesverbrauch nicht zusammen.

Hast du einen Tip ?

 

 

avgpower

173.81

2017-02-11 08:10:42

current

0.69

2017-02-11 08:11:48

energy

637.83

2017-02-11 08:11:48

frequency

50

2017-02-11 08:11:48

pf

0.82

2017-02-11 08:11:48

power

128.9

2017-02-11 08:11:48

state

P: 128.9 E: 637.83 V: 230 C: 0.69 F: 50 Pf: 0.82

2017-02-11 08:11:48

voltage

230

2017-02-11 08:11:48

Sascha
Gast
Sascha

Hallo Daniel.

Danke für deine Antwort. Das Reading „energy“ ist das was die Steckdose bis jetzt komplett gemessen hat.

Ich kann es zwar per „setreading energy 0“ zurück setzen, allerdings nur bis zur nächsten Übertragung der Steckdose. Es gibt auch keine Funktion, um dieses Reading zurück zu setzen, leider.

Ein Resetfunktion für die Dose gibt es nicht. Das heisst, man muss dann immer um 00:00 Uhr die Differenz bilden !?!

Das Reading „power“ ist der aktuelle Verbrauch.

Danke für deine Antwort und für den tollen Blog !!!

Gruß

Sascha

Jörg
Gast
Jörg

Hallo Daniel,

 

ENDLICH !!!

Endlich gibt es eine vernünftige Definition und Statistik der PCA301 Dosen für Tages-/Monats-/Jahreswerte. Bin begeistert.

 

Frage: Da ich 6 dieser Dosen habe, bläst es mir die logfiles so richtig voll. Eben aktuell jede Minute alle Werte.

Wie könnte man das performanter machen, so dass ggf. nur mit eventonchangereading oder nur täglich geloggt wird ?

Jörg
Gast
Jörg

Hallo Daniel,

 

ich habe mal event-on-change-reading .*

eingebaut. Wie du vermutest hattest, bringt es nicht soo viel. Mich wunderst, dass du da keine Performanceprobleme hast. Zwr ist meine Pi auch nur zu ca. 30% ausgelastet – aber in dem Moment in dem dann jede Minute die PCA gelesen und die Werte wiederum ins filelog geschrieben werden, „tanzt“ der perfmon.

 

Eine Lösung wäre daher toll.

 

Grüße

Jörg

 

Tobikus
Gast
Tobikus

Hallo Daniel,
wieder mal super Arbeit von Dir! Vielen Dank dafür. Hat auf Anhieb funktioniert, obwohl ich andere Steckdosen verwende. Perfekt! Weiter so!

wpDiscuz