Herzlichen Dank schon im voraus!

saegefisch



#############################################
#
# A Module to read the values from the Sunny Portal Home Manager.
#
# Adapted version for a linux-server reading the data from the SunnyPortal
# in intervals and push them as an IP-Telegramm to the homeserver
#
# Source of login/read/cookie-core: FHEM Forum: http://forum.fhem.de/index.php/topic,27667.0.html FHEM Wiki:
# Author of login/read/cookie-core: Brun von der Gönne
#
# Author of adapted Version: "saegefisch" in KNX-User-Forum
# Version: 1.0 from 20.05.2015: reflects changes in delivered data structure from SMA sunnyportal (was changed on 19.05.2015)
#
# Feel free to change it to your own needs. Use it on your own risk. But which risk? :)
# - Maybe additional writing into a CSV?
# - Or into an MySQL?
# - Or into NAGIOS getting a fully-featured chart in the "Männervisu"?
# - How could we get the data from the WRs (kWh) in addition (without Blutooth, but via LAN)?
# Please share your changes in the Forum!
#
##############################################
use strict; use warnings; use POSIX; use Data::Dumper; use Time::HiRes qw(gettimeofday); use LWP::UserAgent; use HTTP::Cookies; use IO::Socket::INET;
# Parameters
my $username = '<sma_portaluser>'; # >>>>>> ATTENTION: User/password are visible!!! Use a user with guest-role only (no write permission)!!!
my $password = "<sma-portalpasswort>"; # >>>>>> ATTENTION: User/password are visible!!! Use a user with guest-role only (no write permission)!!!
my $interval = 20; # Update intervall in sec
my $ip_hs = '<IP des HS>'; # IP-Adress of your gira homeserver in your LAN
my $port_hs = '<port>'; # Port (use the same in IP-Telegramm-Settings!)
my $count_err_max = 360; # accepted count of requests with error before job will stop
my $usernameField = "ctl00\$ContentPlaceHolder1\$Logincontrol1\$txtUserName"; # name-tag in HTTML of the input field of the form: User
my $passwordField = "ctl00\$ContentPlaceHolder1\$Logincontrol1\$txtPassword"; # name-tag in HTTML of the input field of the form: Password
my $loginButton = "ctl00\$ContentPlaceHolder1\$Logincontrol1\$LoginBtn"; # name-tag in HTTML of the input field of the form: Absenden-Button
my $url_login = 'https://www.sunnyportal.com/Templates/Start.aspx'; # URL for login
my $url_first = 'https://www.sunnyportal.com/FixedPages/HoManLive.aspx'; # First call after login
my $url_data = 'https://www.sunnyportal.com/homemanager'; # all following calls delivering the data
# Prepare
my $count_err = 0;
my $ua = LWP::UserAgent->new;
# Define user agent type $ua->agent('Mozilla/8.0'); Cookies
$ua->cookie_jar(
HTTP::Cookies->new(
file => './log/mycookies.txt',
ignore_discard => 1,
autosave => 1
)
);
# Log in
my $loginp = $ua->post($url_login,[$usernameField => $username, $passwordField => $password, "__EVENTTARGET" => $loginButton]);
my $testp = $ua->get($url_first);
my $timestamp = time();
# read in intervals as long as error count is low enough
while ($count_err < $count_err_max) {
get_data();
sleep($interval);
}
# -------------
sub get_data {
$testp = $ua->get($url_data);
my ($Sekunden, $Minuten, $Stunden, $Monatstag, $Monat, $Jahr, $Wochentag, $Jahrestag, $Sommerzeit) = localtime(time);
$Monat += 1; $Jahrestag += 1; $Jahr += 1900;
my $send_data = $Jahr . $Monat . $Monatstag . $Stunden . $Minuten . $Sekunden . ";"; # build own timestamp YYYYMMDDhhmmss
if (($testp->content =~ m/FeedIn/i)&&!($testp->content=~ m/expired/i)) {
my $string = $testp->content;
$string =~ s/\{//;
$string =~ s/\}//;
my@array=split(/,/,$string);
foreach (@array){
chomp();
$_ =~ s/"//g;
my ($shm_name, $shm_val) = split(/:/,$_);
# print "$shm_name : $shm_val\n"; # usefull for debugging and testing (output in many lines)
if ($shm_name eq "Timestamp" or $shm_name eq "DateTime" or $shm_name eq "Kind" or $shm_name eq "__type") {next;}
if ($shm_val ne "null" and $shm_val ne '[]' and $shm_val ne '{}') {
$send_data = $send_data . "$shm_val;";
} else {
$send_data = $send_data . ";";
}
}
$send_data = $send_data . "\n";
# Create socket for sending TCP
my $socket = new IO::Socket::INET (
PeerHost => $ip_hs,
PeerPort => $port_hs,
Proto => 'tcp',
);
die "cannot connect to the server $!\n" unless $socket;
my $size = $socket->send($send_data);
# print $send_data; # usefull for debugging and testing (output in one line = CSV-structured)
# print "sent data of length $size\n"; # could be written into a log file
shutdown($socket, 1);
$socket->close();
$count_err = 0;
} else {
$count_err++;
print "ERROR - no proper data from SunnyPortal! Err-Count: $count_err\n";
}
}
Es folgt gleich das Coding zu einer funktionierenden Lösung auf Perl-Basis. Wie es bei mir funktioniert:
{"__type":"LiveDataUI","Timestamp":{"__type":"DateTime","DateTime":"2015-05-19T12:18:57","Kind":"Unspecified"},"PV":7672,"FeedIn":5295,"GridConsumption":0,"DirectConsumption":2357,"SelfConsumption":2377,"SelfSupply":2357,"TotalConsumption":2357,"DirectConsumptionQuote":31,"SelfConsumptionQuote":31,"AutarkyQuote":100,"BatteryIn":20,"BatteryOut":0,"BatteryChargeStatus":99,"OperationHealth":null,"BatteryStateOfHealth":null,"InfoMessages":[],"WarningMessages":[],"ErrorMessages":[],"Info":{}}

{"Timestamp":"\/Date(1431966281348)\/","PV":3013,"FeedIn":2075,"GridConsumption":0,"DirectConsumption":508,"SelfConsumption":938,"SelfSupply":508,"TotalConsumption":508,"DirectConsumptionQuote":17,"SelfConsumptionQuote":31,"AutarkyQuote":100,"BatteryIn":430,"BatteryOut":0,"BatteryChargeStatus":99,"OperationHealth":null,"BatteryStateOfHealth":null,"InfoMessages":[],"WarningMessages":[],"ErrorMessages":[],"Info":{}}

GET /homemanager HTTP/1.0 Authorization: Basic <meinHash> Host: https://www.sunnyportal.com Connection: Close
Wir verarbeiten personenbezogene Daten über die Nutzer unserer Website mithilfe von Cookies und anderen Technologien, um unsere Dienste bereitzustellen. Weitere Informationen findest Du in unserer Datenschutzerklärung.
Indem Du unten auf "ICH stimme zu" klickst, stimmst Du unserer Datenschutzerklärung und unseren persönlichen Datenverarbeitungs- und Cookie-Praktiken zu, wie darin beschrieben. Du erkennst außerdem an, dass dieses Forum möglicherweise außerhalb Deines Landes gehostet wird und bist damit einverstanden, dass Deine Daten in dem Land, in dem dieses Forum gehostet wird, gesammelt, gespeichert und verarbeitet werden.


Einen Kommentar schreiben: