Ich wollte eigentlich nur ein paar Systemwerte auf dem raspberry monitoren und diese per MQTT übertragen - also zu FHEM 'pushen'.
Gibt es einige Lösungen dafür, meistens mit der Schlange programmiert. Die Installation ist mMn immer eine Odyssee. ::)
Deshalb habe ich mal etwas rumprobiert unter dem Vorsatz: möglichst einfach ;)
Heraus gekommen ist ein kurzes Script - einfach und universell einsetzbar. Doku: https://github.com/heinz-otto/raspberry/blob/master/monitor/README.md
Edit: das Script selbst überträgt keine speziellen Daten, es überträgt nur das was in den *.var Dateien steht. Einfache Textdateien, ein Wert pro Zeile.
Wer es ausprobieren will: Man braucht mosquitto_pub (debian: mosquitto-clients), weiter nichts (zumindest auf einem raspbian lite).
Download Script
wget -qO runMqtt.sh https://raw.githubusercontent.com/heinz-otto/raspberry/master/monitor/runMqtt.sh
chmod +x runMqtt.sh
Erzeuge eine config - passend zum MQTT broker
cat >runMqtt.conf <<'EOF'
MQTT_SVR="servername|IP[ -p 1883]"
MQTT_TOPIC="monitor/system"
#MQTT_ACCOUNT="-u user -P password"
MQTT_CID=${HOSTNAME}
EOF
Erzeuge eine Datei mit einer Beispielnachricht
cat >day.var <<'EOF'
MESSAGE="$(date) Nachricht vom runMqtt script"
EOF
Jetzt hat man drei Dateien im gleichen Verzeichnis: runMqtt.sh runMqtt.conf day.var
Einmaliger Start, periodisch geht das mit systemd timer (setup script auf GitHub), crontab oder was auch immer.
./runMqtt.sh
In FHEM, mit MQTT2_SERVER und autocreate aktiv, sollte ein Device erzeugt werden :)
Viel Spaß damit
Otto
Hallo Otto,
Ich hänge mich da mal an. Ich habe etwas ähnliches geschrieben, allerdings in Perl.
root@h-phoscongw:~# cat /usr/local/bin/deCONZrestart.pl
#!/usr/bin/perl
###############################################################################
#
# Developed with Kate
#
# (c) 2019 Copyright: Marko Oldenburg (marko.oldenburg at araneaconsult dot de)
# All rights reserved
#
#
# This script is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# any later version.
#
# The GNU General Public License can be found at
# http://www.gnu.org/copyleft/gpl.html.
# A copy is found in the textfile GPL.txt and important notices to the license
# from the author is found in LICENSE.txt distributed with these scripts.
#
# This script is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
#
###############################################################################
use strict;
use warnings;
use POSIX;
use IO::Socket::INET;
##################################################
# Forward declarations
#
sub deconzDaemonSystemctl($$);
sub deconzDaemonState($);
sub sendStateToFHEM();
sub deconzDaemonCpuLast();
##################################################
# Variables:
my $self = {};
$self->{daemons} = ['deconz','deconz-wifi'];
###################################################
# Start the program
my ($arg,$debug,$acount);
exit 'Usage status|restart' unless ( scalar(@ARGV) > 0 );
$arg = shift @ARGV;
$debug = 0;
if ( $arg eq 'restart' ) {
deconzDaemonSystemctl('restart',$self->{daemons}->[0]);
deconzDaemonSystemctl('stop',$self->{daemons}->[1]);
}
$acount = 0;
foreach ( @{ $self->{daemons} } ) {
deconzDaemonState($self->{daemons}->[$acount]);
$acount++;
}
deconzDaemonCpuLast() if ( $arg eq 'restart' or $arg eq 'status' );
sendStateToFHEM();
sub deconzDaemonSystemctl($$) {
my ( $ctlCmd, $daemon ) = @_;
system('systemctl ' . $ctlCmd . ' ' . $daemon);
return 0;
}
sub deconzDaemonState($) {
my $daemon = shift;
$self->{daemons}->[$acount] = { daemon => $daemon };
if ( open( STATE, "systemctl status $daemon 2>&1 |" ) ) {
while ( my $line = <STATE> ) {
chomp($line);
print qq($line\n) if ( $debug == 1 );
if ( $line =~ m#^\s+Loaded:\s(\S+)# ) {
$self->{daemons}->[$acount]->{loaded} = $1;
}
elsif ( $line =~ m#^^\s+Active:\s(\S+\s\S+)\s\S+\s(\S+\s\S+\s\S+\s\S+);\s(\S+)# ) {
$self->{daemons}->[$acount]->{active} = $1;
$self->{daemons}->[$acount]->{timestamp} = $2;
$self->{daemons}->[$acount]->{timeago} = $3;
}
}
close(STATE);
}
else {
die "Couldn't use STATE: $!\n";
$self->{daemons}->[$acount]->{error} = 'Couldn\'t use STATE: ' . $;;
return 1;
}
return 0;
}
sub deconzDaemonCpuLast() {
if ( open( STATE, 'ps uax 2>&1 |' ) ) {
while ( my $line = <STATE> ) {
chomp($line);
print qq($line\n) if ( $debug == 1 );
if ( $line =~ m#^marko\s+\d+\s+(\d+.\d*).+\/usr\/bin\/deCONZ# ) {
$self->{daemons}->[0]->{cpuLast} = $1;
}
}
close(STATE);
}
else {
die "Couldn't use STATE: $!\n";
$self->{daemons}->[0]->{error} = 'Couldn\'t use STATE: ' . $;;
return 1;
}
return 0;
}
sub sendStateToFHEM() {
my $fhemDummy = 'dummyDeconzDaemonState';
print 'test' . "\n";
my $HOSTNAME = "p-fhem.tuxnet.lan";
my $HOSTPORT = "7072";
my $socket = IO::Socket::INET->new('PeerAddr' => $HOSTNAME,'PeerPort' => $HOSTPORT,'Proto' => 'tcp')
or die 'Cant\'t connect to FHEM Instance';
$acount = 0;
foreach ( @{ $self->{daemons} } ) {
while ( my ( $r, $v ) = each %{$self->{daemons}->[$acount]} ) {
$socket->print('setreading ' . $fhemDummy . ' ' . $self->{daemons}->[$acount]->{daemon} . '_' . $r . ' ' . $v . "\n") if ( $v ne $self->{daemons}->[$acount]->{daemon} );
$socket->print('setreading ' . $fhemDummy . ' state ' . $v ."\n") if ( $r eq 'active' and $self->{daemons}->[$acount]->{daemon} eq 'deconz' );
}
$acount++;
}
$socket->close;
}
Abgefragt werden die Zustände meines DeConz Dienstes. Die erhaltenen Werte und Zustände werden dann an einen Dummy in FHEM als Reading gesendet.
Coole Idee. Ich nutze seit Langem ein periodisch laufendes Script (https://forum.fhem.de/index.php/topic,129731.msg1240058.html#msg1240058) welches ein json-String via mosquitto_pub an FHEM-MQTT server sendet. Für Systemparameter reicht das mehr als genug - ua auch ob Service etc laufen.