veraltete werte löschen oder ersetzen ?

Begonnen von Klaus0815, 18 Oktober 2015, 20:12:25

Vorheriges Thema - Nächstes Thema

Klaus0815

Ich habe hier mehrere Sensoren, die zyklisch ihre Werte an FHEM schicken ( z.B. MySensors)

Andere Dienste greifen auf FHEM über Telnet zu, um diese Werte abzufragen und dann Aktionen auszulösen.

Es kann jetzt vorkommen, das mir zwar Sensor X 21° anzeigt, der Wert aber schon mehrere Tage alt ist (z.B. weil die Batterie im Sender leer)

Gibt es eine rel. einfache Möglichkeit, z.B. Sensorwerte nach x Minuten ohne Update mit einem Wert wie 0 oder 125 zu überschreiben ? 
Es wäre dann rel. einfach, diese als ungültig zu verwerten

Oder wie würdet ihr so was lösen ?

viegener

Ich prüfen in diesen Fällen den Zeitstempel des Readings, das ist ja auch über telnet möglich.

Um das einfacher zu machen, habe ich auch ein userReading bei meinen Sensoren gemacht, dass die Zeit seit dem letzten Readings update enthält. Dadurch steht da soetwas wie

lastUpdate 3m

Das ist für mich auch als Mensch leichter zu lesen als erst zwei Zeitstempel voneinander abzuziehen...


Kein Support über PM - Anfragen gerne im Forum - Damit auch andere profitieren und helfen können

Klaus0815

Hallo viegener,

wie genau machst Du das ?
Ich benutze zugegeben FHEM nur als Schnittstelle zu den verschiedenen Sensoren, mache meine ganzen Aktionen selber über bash-Skripts.
Wie erstellt man ein userreading ?

Viele Grüße

Klaus

viegener

OK, ich hinterfrage das mit den bash-scripts nicht, aber da fhem an sich alle Möglichkeiten bietet erscheint es mir geeignet viele Aktionen dort zu erledigen.

Userreading --> siehe Commandref

Mein userreading ist folgendermassen definiert:
lastupdate {getTimeDiffDesc( getNewestTimestamp("temp_gb", "battery", "temperature","humidity" ) )}

Wobei
getTimeDiffDesc und getNewestTimestamp, eigene perlfunktionen sind, um die Berechnungen direkt in fhem durchzuführen.

Wenn Du bash scripts verwendest würde ich annehmen, dass Du die Berechnungen eher in der bash durchführen willst. Du kannst ja den Zeitstempel wie gesagt auch über telnet holen.

Johannes
Kein Support über PM - Anfragen gerne im Forum - Damit auch andere profitieren und helfen können

Klaus0815

Halo Johannes,

ich bin zugegeben nur Hobbyprogrammierer

Würdest Du die Perl-Funktionen, die hinter getTimeDiffDesc und getNewestTimestamp stehen veröffentlichen ?

viegener

Klar, auch wenn ich nicht behaupte dass diese besonders genial sind...

Also in meiner 99_myUtils.pm sind sie wie folgt definiert:




##############################################
# Berechne Zeitdifferenz von String zeit -> als Beschreibung
#
sub getTimeDiffDesc($) {

  my ($str) = @_;
 
  my $now = time;

  my $td = $now - time_str2num( $str );

  my $tstr = "???";
 
  if ( $td < 1 ) {
    $tstr = "<1m";
  } elsif ( $td < 60 ) {
    $tstr = "<1m";
  } elsif ( $td < 3600 ) {
    $tstr = sprintf("%2d", int(($td/60) + 0.5) )."m" ;
  } elsif ( $td < (3600*24) ) {
    $tstr = sprintf("%2d", int(($td/3600) + 0.5) )."h" ;
  } else {
    $tstr = int(($td/(3600*24)) + 0.5)."d" ;
  }
 
  return $tstr;
}


##############################################
# Berechne neuesten Zeitstempel von mehreren Stati
#
sub getNewestTimestamp($@) {

my ($device, @args) = @_;

  my $nt = 0;
  my $nts = "";
 
  for(my $i=0; $i < int(@args); $i++) {
    my $tds = ReadingsTimestamp($device,$args[$i],"");
    if ( $tds ne "" ) {
      my $td = time_str2num( $tds );
      if ( $nt == 0 ) {
        $nt = $td;
        $nts = $tds;
      } elsif ( $td > $nt ) {
        $nt = $td;
        $nts = $tds;
      }
    }
  }
 
# Log 1, "getNewestTimestamp: $device  :$nts:";
  return $nts;
}



getTimeDiffDesc ist dafür da eine lesbare Info zur Zeitdifferenz zu bekommen, um z.B. statt 7200s eine Umwandung in 2h durchzuführen. Ein Alter unterhalb 1m ist für mich irrelevant, deshalb gibt es <1m für alles unter 60 sec.

Johannes
Kein Support über PM - Anfragen gerne im Forum - Damit auch andere profitieren und helfen können