mirror of
https://github.com/fhem/fhem-mirror.git
synced 2025-05-04 22:19:38 +00:00
76_SMAPortal: internal code changes, bug fixes show weather_icon
git-svn-id: https://svn.fhem.de/fhem/trunk/fhem@22160 2b470e98-0d58-463d-a4d8-8e2adae1ed80
This commit is contained in:
parent
01a32ec7e7
commit
78ac6cf921
1
CHANGED
1
CHANGED
@ -1,5 +1,6 @@
|
|||||||
# Add changes at the top of the list. Keep it in ASCII, and 80-char wide.
|
# Add changes at the top of the list. Keep it in ASCII, and 80-char wide.
|
||||||
# Do not insert empty lines here, update check depends on it.
|
# Do not insert empty lines here, update check depends on it.
|
||||||
|
- bugfix: 76_SMAPortal: internal code changes, bug fixes show weather_icon
|
||||||
- changed: 76_SMAPortal: internal code changes, minor bug fixes
|
- changed: 76_SMAPortal: internal code changes, minor bug fixes
|
||||||
- bugfix: 70_BRAVIA: fix register procedure
|
- bugfix: 70_BRAVIA: fix register procedure
|
||||||
- change: 32_withings: added sleep apnea readings
|
- change: 32_withings: added sleep apnea readings
|
||||||
|
@ -135,6 +135,7 @@ BEGIN {
|
|||||||
|
|
||||||
# Versions History intern
|
# Versions History intern
|
||||||
my %vNotesIntern = (
|
my %vNotesIntern = (
|
||||||
|
"2.10.3" => "11.06.2020 internal code changes, bug fixes show weather_icon ",
|
||||||
"2.10.2" => "10.06.2020 bug fixes get/switch consumers ",
|
"2.10.2" => "10.06.2020 bug fixes get/switch consumers ",
|
||||||
"2.10.1" => "08.06.2020 internal code changes, bug fixes ",
|
"2.10.1" => "08.06.2020 internal code changes, bug fixes ",
|
||||||
"2.10.0" => "03.06.2020 refactored login process ",
|
"2.10.0" => "03.06.2020 refactored login process ",
|
||||||
@ -212,6 +213,18 @@ my %statkeys = ( # Statistikdaten auszulesende Schlüs
|
|||||||
AutarkyRate => 1,
|
AutarkyRate => 1,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
# Tags der verfügbaren Datenquellen
|
||||||
|
my @pd = qw( balanceDayData
|
||||||
|
liveData
|
||||||
|
weatherData
|
||||||
|
forecastData
|
||||||
|
consumerLiveData
|
||||||
|
consumerDayData
|
||||||
|
consumerMonthData
|
||||||
|
consumerYearData
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
###############################################################
|
###############################################################
|
||||||
# SMAPortal Initialize
|
# SMAPortal Initialize
|
||||||
@ -219,6 +232,7 @@ my %statkeys = ( # Statistikdaten auszulesende Schlüs
|
|||||||
sub Initialize {
|
sub Initialize {
|
||||||
my ($hash) = @_;
|
my ($hash) = @_;
|
||||||
|
|
||||||
|
my $v5d = join ",", @pd;
|
||||||
$hash->{DefFn} = \&Define;
|
$hash->{DefFn} = \&Define;
|
||||||
$hash->{UndefFn} = \&Undefine;
|
$hash->{UndefFn} = \&Undefine;
|
||||||
$hash->{DeleteFn} = \&Delete;
|
$hash->{DeleteFn} = \&Delete;
|
||||||
@ -232,7 +246,7 @@ sub Initialize {
|
|||||||
"interval ".
|
"interval ".
|
||||||
"showPassInLog:1,0 ".
|
"showPassInLog:1,0 ".
|
||||||
"userAgent ".
|
"userAgent ".
|
||||||
"verbose5Data:none,loginData,balanceDayData,liveData,weatherData,forecastData,consumerLiveData,consumerDayData,consumerMonthData,consumerYearData ".
|
"verbose5Data:none,loginData,".$v5d." ".
|
||||||
$readingFnAttributes;
|
$readingFnAttributes;
|
||||||
|
|
||||||
eval { FHEM::Meta::InitMod( __FILE__, $hash ) }; ## no critic 'eval' # für Meta.pm (https://forum.fhem.de/index.php/topic,97589.0.html)
|
eval { FHEM::Meta::InitMod( __FILE__, $hash ) }; ## no critic 'eval' # für Meta.pm (https://forum.fhem.de/index.php/topic,97589.0.html)
|
||||||
@ -753,19 +767,17 @@ sub GetSetData { ## no cri
|
|||||||
my ($string) = @_;
|
my ($string) = @_;
|
||||||
my ($name,$getp,$setp) = split("\\|",$string);
|
my ($name,$getp,$setp) = split("\\|",$string);
|
||||||
my $hash = $defs{$name};
|
my $hash = $defs{$name};
|
||||||
my $errstate = 0;
|
|
||||||
my $useragent = AttrVal($name, "userAgent", "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; Trident/6.0)");
|
my $useragent = AttrVal($name, "userAgent", "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; Trident/6.0)");
|
||||||
my $cookieLocation = AttrVal($name, "cookieLocation", "./log/".$name."_cookie.txt");
|
my $cookieLocation = AttrVal($name, "cookieLocation", "./log/".$name."_cookie.txt");
|
||||||
my $v5d = AttrVal($name, "verbose5Data", "none");
|
my $v5d = AttrVal($name, "verbose5Data", "none");
|
||||||
my $dl = AttrVal($name, "detailLevel", 1); # selected Detail Level
|
my $dl = AttrVal($name, "detailLevel", 1); # selected Detail Level
|
||||||
my $state = "ok";
|
my $state = "ok";
|
||||||
my ($reread,$retry) = (0,0);
|
|
||||||
my ($exceed,$newcycle) = (0,0);
|
|
||||||
my ($st,$lc) = ("","");
|
my ($st,$lc) = ("","");
|
||||||
my @da = ();
|
my @da = ();
|
||||||
my ($ccdaydata_content,$ccmonthdata_content,$ccyeardata_content) = ("","","");
|
|
||||||
my ($d,$op,$paref);
|
|
||||||
|
|
||||||
|
my ($errstate,$reread,$retry,$exceed,$newcycle) = (0,0,0,0,0);
|
||||||
|
|
||||||
|
my ($d,$op);
|
||||||
if($setp ne "none") {
|
if($setp ne "none") {
|
||||||
# Verbraucher soll in den Status $op geschaltet werden
|
# Verbraucher soll in den Status $op geschaltet werden
|
||||||
($d,$op) = split(":",$setp);
|
($d,$op) = split(":",$setp);
|
||||||
@ -803,7 +815,7 @@ sub GetSetData { ## no cri
|
|||||||
|
|
||||||
### Login
|
### Login
|
||||||
##############
|
##############
|
||||||
$paref = [ $name, $ua, $state, $errstate ];
|
my $paref = [ $name, $ua, $state, $errstate ];
|
||||||
($state, $errstate) = _checkLogin ($paref);
|
($state, $errstate) = _checkLogin ($paref);
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
@ -854,16 +866,14 @@ sub GetSetData { ## no cri
|
|||||||
|
|
||||||
### Live-Daten
|
### Live-Daten
|
||||||
################
|
################
|
||||||
my ($livedata,$livedata_content) = _getData ({ name => $name,
|
($errstate,$state,$reread,$retry) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => 'https://www.sunnyportal.com/homemanager?t='.$time,
|
call => 'https://www.sunnyportal.com/homemanager?t='.$time,
|
||||||
tag => "liveData"
|
tag => "liveData",
|
||||||
});
|
|
||||||
|
|
||||||
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
|
||||||
errstate => $errstate,
|
|
||||||
state => $state,
|
state => $state,
|
||||||
data => $livedata
|
fnaref => [ qw( extractLiveData ) ],
|
||||||
|
addon => "",
|
||||||
|
daref => \@da
|
||||||
});
|
});
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
@ -899,36 +909,24 @@ sub GetSetData { ## no cri
|
|||||||
return "$name|$exceed|$newcycle|$errstate|$getp|$setp";
|
return "$name|$exceed|$newcycle|$errstate|$getp|$setp";
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($livedata_content && $livedata_content !~ m/undefined/ix) {
|
|
||||||
extractLiveData ($hash,\@da,$livedata_content);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
### Wetterdaten
|
### Wetterdaten
|
||||||
#####################
|
#####################
|
||||||
my ($weatherdata,$weatherdata_content) = _getData ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => 'https://www.sunnyportal.com/Dashboard/Weather',
|
call => 'https://www.sunnyportal.com/Dashboard/Weather',
|
||||||
tag => "weatherData"
|
tag => "weatherData",
|
||||||
});
|
|
||||||
|
|
||||||
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
|
||||||
errstate => $errstate,
|
|
||||||
state => $state,
|
state => $state,
|
||||||
data => $weatherdata
|
fnaref => [ qw( extractWeatherData ) ],
|
||||||
|
addon => "",
|
||||||
|
daref => \@da
|
||||||
});
|
});
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
$st = encode_base64 ( $state,"");
|
$st = encode_base64 ( $state,"");
|
||||||
return "$name|0|0|$errstate|$getp|$setp|$st";
|
return "$name|0|0|$errstate|$getp|$setp|$st";
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($weatherdata_content && $weatherdata_content !~ m/undefined/ix) {
|
|
||||||
extractWeatherData ($hash,\@da,$weatherdata_content);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@ -939,56 +937,40 @@ sub GetSetData { ## no cri
|
|||||||
my %fields = ("Content-Type" => "application/json; charset=utf-8");
|
my %fields = ("Content-Type" => "application/json; charset=utf-8");
|
||||||
my $cont = qq{ {"tabNumber":$tab,"anchorTime":$anchort} };
|
my $cont = qq{ {"tabNumber":$tab,"anchorTime":$anchort} };
|
||||||
|
|
||||||
my ($balancedataday,$balancedataday_content) = _putData ({ name => $name,
|
($errstate,$state) = _dispatchPost ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => 'https://www.sunnyportal.com/FixedPages/HoManEnergyRedesign.aspx/GetLegendWithValues',
|
call => 'https://www.sunnyportal.com/FixedPages/HoManEnergyRedesign.aspx/GetLegendWithValues',
|
||||||
|
tag => "balanceDayData",
|
||||||
|
state => $state,
|
||||||
|
fnaref => [ qw( extractStatisticData ) ],
|
||||||
fields => \%fields,
|
fields => \%fields,
|
||||||
content => $cont,
|
content => $cont,
|
||||||
tag => "balanceDayData"
|
addon => "Day",
|
||||||
|
daref => \@da
|
||||||
});
|
});
|
||||||
|
|
||||||
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
|
||||||
errstate => $errstate,
|
|
||||||
state => $state,
|
|
||||||
data => $balancedataday
|
|
||||||
});
|
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
$st = encode_base64 ( $state,"");
|
$st = encode_base64 ( $state,"");
|
||||||
return "$name|0|0|$errstate|$getp|$setp|$st";
|
return "$name|0|0|$errstate|$getp|$setp|$st";
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($balancedataday_content && $balancedataday_content !~ m/undefined/ix) {
|
|
||||||
extractStatisticData ($hash,\@da,$balancedataday_content,"Day");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
### Forecast Daten abrufen
|
### Forecast Daten abrufen
|
||||||
###########################
|
###########################
|
||||||
if($dl > 1) {
|
if($dl > 1) {
|
||||||
my ($forecastdata,$forecastdata_content) = _getData ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => 'https://www.sunnyportal.com/HoMan/Forecast/LoadRecommendationData',
|
call => 'https://www.sunnyportal.com/HoMan/Forecast/LoadRecommendationData',
|
||||||
tag => "forecastData"
|
tag => "forecastData",
|
||||||
});
|
|
||||||
|
|
||||||
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
|
||||||
errstate => $errstate,
|
|
||||||
state => $state,
|
state => $state,
|
||||||
data => $forecastdata
|
fnaref => [ qw( extractPlantData extractForecastData extractConsumerData ) ],
|
||||||
|
addon => "",
|
||||||
|
daref => \@da
|
||||||
});
|
});
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
$st = encode_base64 ($state, "");
|
$st = encode_base64 ( $state,"");
|
||||||
return "$name|0|0|$errstate|$getp|$setp|$st";
|
return "$name|0|0|$errstate|$getp|$setp|$st";
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($forecastdata_content && $forecastdata_content !~ m/undefined/ix) {
|
|
||||||
extractPlantData ($hash,\@da,$forecastdata_content);
|
|
||||||
extractForecastData ($hash,\@da,$forecastdata_content);
|
|
||||||
extractConsumerData ($hash,\@da,$forecastdata_content);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -997,27 +979,20 @@ sub GetSetData { ## no cri
|
|||||||
### Consumer Livedaten und historische Energiedaten
|
### Consumer Livedaten und historische Energiedaten
|
||||||
#####################################################
|
#####################################################
|
||||||
if($dl > 2) {
|
if($dl > 2) {
|
||||||
my ($consumerlivedata,$consumerlivedata_content) = _getData ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => 'https://www.sunnyportal.com/Homan/ConsumerBalance/GetLiveProxyValues',
|
call => 'https://www.sunnyportal.com/Homan/ConsumerBalance/GetLiveProxyValues',
|
||||||
tag => "consumerLiveData"
|
tag => "consumerLiveData",
|
||||||
});
|
|
||||||
|
|
||||||
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
|
||||||
errstate => $errstate,
|
|
||||||
state => $state,
|
state => $state,
|
||||||
data => $consumerlivedata
|
fnaref => [ qw( extractConsumerLiveData ) ],
|
||||||
|
addon => "",
|
||||||
|
daref => \@da
|
||||||
});
|
});
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
$st = encode_base64 ( $state,"");
|
$st = encode_base64 ( $state,"");
|
||||||
return "$name|0|0|$errstate|$getp|$setp|$st";
|
return "$name|0|0|$errstate|$getp|$setp|$st";
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($consumerlivedata_content && $consumerlivedata_content !~ m/undefined/ix) {
|
|
||||||
extractConsumerLiveData ($hash,\@da,$consumerlivedata_content);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
if($hash->{HELPER}{PLANTOID}) {
|
if($hash->{HELPER}{PLANTOID}) {
|
||||||
my $PlantOid = $hash->{HELPER}{PLANTOID};
|
my $PlantOid = $hash->{HELPER}{PLANTOID};
|
||||||
@ -1044,12 +1019,12 @@ sub GetSetData { ## no cri
|
|||||||
Log3 ($name, 4, "$name - Request date -> start: $dds, end: $dde");
|
Log3 ($name, 4, "$name - Request date -> start: $dds, end: $dde");
|
||||||
Log3 ($name, 5, "$name - Request consumer current day data string ->\n$ccdd");
|
Log3 ($name, 5, "$name - Request consumer current day data string ->\n$ccdd");
|
||||||
|
|
||||||
($errstate,$state) = _dispatch ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => $ccdd,
|
call => $ccdd,
|
||||||
tag => "consumerDayData",
|
tag => "consumerDayData",
|
||||||
state => $state,
|
state => $state,
|
||||||
function => "extractConsumerHistData",
|
fnaref => [ qw( extractConsumerHistData ) ],
|
||||||
addon => "day",
|
addon => "day",
|
||||||
daref => \@da
|
daref => \@da
|
||||||
});
|
});
|
||||||
@ -1063,12 +1038,12 @@ sub GetSetData { ## no cri
|
|||||||
Log3 ($name, 4, "$name - Request date -> start: $mds, end: $mde");
|
Log3 ($name, 4, "$name - Request date -> start: $mds, end: $mde");
|
||||||
Log3 ($name, 5, "$name - Request consumer current month data string ->\n$ccmd");
|
Log3 ($name, 5, "$name - Request consumer current month data string ->\n$ccmd");
|
||||||
|
|
||||||
($errstate,$state) = _dispatch ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => $ccmd,
|
call => $ccmd,
|
||||||
tag => "consumerMonthData",
|
tag => "consumerMonthData",
|
||||||
state => $state,
|
state => $state,
|
||||||
function => "extractConsumerHistData",
|
fnaref => [ qw( extractConsumerHistData ) ],
|
||||||
addon => "month",
|
addon => "month",
|
||||||
daref => \@da
|
daref => \@da
|
||||||
});
|
});
|
||||||
@ -1082,12 +1057,12 @@ sub GetSetData { ## no cri
|
|||||||
Log3 ($name, 4, "$name - Request date -> start: $yds, end: $yde");
|
Log3 ($name, 4, "$name - Request date -> start: $yds, end: $yde");
|
||||||
Log3 ($name, 5, "$name - Request consumer current year data string ->\n$ccyd");
|
Log3 ($name, 5, "$name - Request consumer current year data string ->\n$ccyd");
|
||||||
|
|
||||||
($errstate,$state) = _dispatch ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => $ccyd,
|
call => $ccyd,
|
||||||
tag => "consumerYearData",
|
tag => "consumerYearData",
|
||||||
state => $state,
|
state => $state,
|
||||||
function => "extractConsumerHistData",
|
fnaref => [ qw( extractConsumerHistData ) ],
|
||||||
addon => "year",
|
addon => "year",
|
||||||
daref => \@da
|
daref => \@da
|
||||||
});
|
});
|
||||||
@ -1198,16 +1173,16 @@ return ($state, $errstate);
|
|||||||
}
|
}
|
||||||
|
|
||||||
################################################################
|
################################################################
|
||||||
# Dispatcher
|
# Dispatcher GET
|
||||||
################################################################
|
################################################################
|
||||||
sub _dispatch {
|
sub _dispatchGet {
|
||||||
my $paref = shift;
|
my $paref = shift;
|
||||||
my $name = $paref->{name};
|
my $name = $paref->{name};
|
||||||
my $ua = $paref->{ua}; # LWP Useragent
|
my $ua = $paref->{ua}; # LWP Useragent
|
||||||
my $call = $paref->{call}; # Seitenaufruf zur Datenquelle
|
my $call = $paref->{call}; # Seitenaufruf zur Datenquelle
|
||||||
my $tag = $paref->{tag}; # Kennzeichen der abzurufenen Daten
|
my $tag = $paref->{tag}; # Kennzeichen der abzurufenen Daten
|
||||||
my $state = $paref->{state};
|
my $state = $paref->{state};
|
||||||
my $fn = $paref->{function}; # aufzurufende Funktion zur Datenextraktion
|
my $fnref = $paref->{fnaref}; # Referenz zu Array der aufzurufenden Funktion(en) zur Datenextraktion
|
||||||
my $fnaddon = $paref->{addon}; # optionales Addon für aufzurufende Funktion
|
my $fnaddon = $paref->{addon}; # optionales Addon für aufzurufende Funktion
|
||||||
my $daref = $paref->{daref}; # Referenz zum Datenarray
|
my $daref = $paref->{daref}; # Referenz zum Datenarray
|
||||||
my $hash = $defs{$name};
|
my $hash = $defs{$name};
|
||||||
@ -1226,15 +1201,65 @@ sub _dispatch {
|
|||||||
data => $data
|
data => $data
|
||||||
});
|
});
|
||||||
|
|
||||||
return ($errstate,$state) if($errstate);
|
return ($errstate,$state,$reread,$retry) if($errstate || $reread || $retry);
|
||||||
|
|
||||||
if ($data_cont && $data_cont !~ m/undefined/ix) {
|
if ($data_cont && $data_cont !~ m/undefined/ix) {
|
||||||
|
my @func = @$fnref;
|
||||||
no strict "refs"; ## no critic 'NoStrict'
|
no strict "refs"; ## no critic 'NoStrict'
|
||||||
|
for my $fn (@func) {
|
||||||
&{$fn} ($hash,$daref,$data_cont,$fnaddon);
|
&{$fn} ($hash,$daref,$data_cont,$fnaddon);
|
||||||
|
}
|
||||||
use strict "refs";
|
use strict "refs";
|
||||||
}
|
}
|
||||||
|
|
||||||
return ($errstate,$state);
|
return ($errstate,$state,$reread,$retry);
|
||||||
|
}
|
||||||
|
|
||||||
|
################################################################
|
||||||
|
# Dispatcher POST
|
||||||
|
################################################################
|
||||||
|
sub _dispatchPost {
|
||||||
|
my $paref = shift;
|
||||||
|
my $name = $paref->{name};
|
||||||
|
my $ua = $paref->{ua}; # LWP Useragent
|
||||||
|
my $call = $paref->{call}; # Seitenaufruf zur Datenquelle
|
||||||
|
my $tag = $paref->{tag}; # Kennzeichen der abzurufenen Daten
|
||||||
|
my $state = $paref->{state};
|
||||||
|
my $fnref = $paref->{fnaref}; # Referenz zu Array der aufzurufenden Funktion(en) zur Datenextraktion
|
||||||
|
my $fields = $paref->{fields}; # Referenz zum Hash der zu übertragenden PUSH Header
|
||||||
|
my $cont = $paref->{content}; # Content Daten für PUSH (String)
|
||||||
|
my $fnaddon = $paref->{addon}; # optionales Addon für aufzurufende Funktion
|
||||||
|
my $daref = $paref->{daref}; # Referenz zum Datenarray
|
||||||
|
my $hash = $defs{$name};
|
||||||
|
|
||||||
|
my ($reread,$retry,$errstate) = (0,0,0);
|
||||||
|
|
||||||
|
my ($data,$data_cont) = _postData ({ name => $name,
|
||||||
|
ua => $ua,
|
||||||
|
call => $call,
|
||||||
|
tag => $tag,
|
||||||
|
fields => $fields,
|
||||||
|
content => $cont,
|
||||||
|
});
|
||||||
|
|
||||||
|
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
||||||
|
errstate => $errstate,
|
||||||
|
state => $state,
|
||||||
|
data => $data
|
||||||
|
});
|
||||||
|
|
||||||
|
return ($errstate,$state) if($errstate);
|
||||||
|
|
||||||
|
if ($data_cont && $data_cont !~ m/undefined/ix) {
|
||||||
|
my @func = @$fnref;
|
||||||
|
no strict "refs"; ## no critic 'NoStrict'
|
||||||
|
for my $fn (@func) {
|
||||||
|
&{$fn} ($hash,$daref,$data_cont,$fnaddon);
|
||||||
|
}
|
||||||
|
use strict "refs";
|
||||||
|
}
|
||||||
|
|
||||||
|
return ($errstate,$state,$reread,$retry);
|
||||||
}
|
}
|
||||||
|
|
||||||
################################################################
|
################################################################
|
||||||
@ -1268,7 +1293,7 @@ return ($data,$dcont);
|
|||||||
################################################################
|
################################################################
|
||||||
# Standard Abruf Daten POST
|
# Standard Abruf Daten POST
|
||||||
################################################################
|
################################################################
|
||||||
sub _putData {
|
sub _postData {
|
||||||
my $paref = shift;
|
my $paref = shift;
|
||||||
my $name = $paref->{name};
|
my $name = $paref->{name};
|
||||||
my $ua = $paref->{ua};
|
my $ua = $paref->{ua};
|
||||||
@ -1692,7 +1717,7 @@ sub extractForecastData { ## no critic 'complexity'
|
|||||||
push @$daref, "L4_${time_str}_Total:". (int($fc_obj->{'PvMeanPower'}->{'Amount'}) - int($fc_obj->{'ConsumptionForecast'}->{'Amount'} / 3600))." Wh";
|
push @$daref, "L4_${time_str}_Total:". (int($fc_obj->{'PvMeanPower'}->{'Amount'}) - int($fc_obj->{'ConsumptionForecast'}->{'Amount'} / 3600))." Wh";
|
||||||
|
|
||||||
# add WeatherId Helper to show weather icon
|
# add WeatherId Helper to show weather icon
|
||||||
$hash->{HELPER}{"L4_".${time_str}."_WeatherId"} = int($fc_obj->{'WeatherId'}) if(defined $fc_obj->{'WeatherId'});
|
BlockingInformParent("FHEM::SMAPortal::setFromBlocking", [$name, "NULL", "L4_".${time_str}."_WeatherId:".int($fc_obj->{'WeatherId'}) ], 1) if(defined $fc_obj->{'WeatherId'});
|
||||||
}
|
}
|
||||||
if($time_str =~ /ThisHour/x && $dl >= 2) {
|
if($time_str =~ /ThisHour/x && $dl >= 2) {
|
||||||
push @$daref, "L2_${time_str}_Time:". TimeAdjust($hash,$fc_obj->{'TimeStamp'}->{'DateTime'},$tkind);
|
push @$daref, "L2_${time_str}_Time:". TimeAdjust($hash,$fc_obj->{'TimeStamp'}->{'DateTime'},$tkind);
|
||||||
@ -1702,7 +1727,7 @@ sub extractForecastData { ## no critic 'complexity'
|
|||||||
push @$daref, "L2_${time_str}_Total:". (int($fc_obj->{'PvMeanPower'}->{'Amount'}) - int($fc_obj->{'ConsumptionForecast'}->{'Amount'} / 3600))." Wh";
|
push @$daref, "L2_${time_str}_Total:". (int($fc_obj->{'PvMeanPower'}->{'Amount'}) - int($fc_obj->{'ConsumptionForecast'}->{'Amount'} / 3600))." Wh";
|
||||||
|
|
||||||
# add WeatherId Helper to show weather icon
|
# add WeatherId Helper to show weather icon
|
||||||
$hash->{HELPER}{"L2_".${time_str}."_WeatherId"} = int($fc_obj->{'WeatherId'}) if(defined $fc_obj->{'WeatherId'});
|
BlockingInformParent("FHEM::SMAPortal::setFromBlocking", [$name, "NULL", "L2_".${time_str}."_WeatherId:".int($fc_obj->{'WeatherId'}) ], 1) if(defined $fc_obj->{'WeatherId'});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -2485,7 +2510,7 @@ sub PortalAsHtml {
|
|||||||
$di{0} = $pv{0} - $co{0};
|
$di{0} = $pv{0} - $co{0};
|
||||||
$is{0} = (ReadingsVal($name,"L2_ThisHour_IsConsumptionRecommended",'no') eq 'yes' ) ? $icon : undef;
|
$is{0} = (ReadingsVal($name,"L2_ThisHour_IsConsumptionRecommended",'no') eq 'yes' ) ? $icon : undef;
|
||||||
$we{0} = $hash->{HELPER}{L2_ThisHour_WeatherId} if($weather); # für Wettericons
|
$we{0} = $hash->{HELPER}{L2_ThisHour_WeatherId} if($weather); # für Wettericons
|
||||||
$we{0} = $we{0}?$we{0}:0;
|
$we{0} = $we{0} ? $we{0} : 999;
|
||||||
|
|
||||||
if(AttrVal("global","language","EN") eq "DE") {
|
if(AttrVal("global","language","EN") eq "DE") {
|
||||||
(undef,undef,undef,$t{0}) = ReadingsVal($name,"L2_ThisHour_Time",'0') =~ m/(\d{2}).(\d{2}).(\d{4})\s(\d{2})/x;
|
(undef,undef,undef,$t{0}) = ReadingsVal($name,"L2_ThisHour_Time",'0') =~ m/(\d{2}).(\d{2}).(\d{4})\s(\d{2})/x;
|
||||||
@ -2558,7 +2583,7 @@ sub PortalAsHtml {
|
|||||||
|
|
||||||
$is{$i} = (ReadingsVal($name,"L4_NextHour".sprintf("%02d",$i)."_IsConsumptionRecommended",'no') eq 'yes') ? $icon : undef;
|
$is{$i} = (ReadingsVal($name,"L4_NextHour".sprintf("%02d",$i)."_IsConsumptionRecommended",'no') eq 'yes') ? $icon : undef;
|
||||||
$we{$i} = $hash->{HELPER}{"L4_NextHour".sprintf("%02d",$i)."_WeatherId"} if($weather); # für Wettericons
|
$we{$i} = $hash->{HELPER}{"L4_NextHour".sprintf("%02d",$i)."_WeatherId"} if($weather); # für Wettericons
|
||||||
$we{$i} = $we{$i}?$we{$i}:0;
|
$we{$i} = $we{$i} ? $we{$i} : 999;
|
||||||
|
|
||||||
if(AttrVal("global","language","EN") eq "DE") {
|
if(AttrVal("global","language","EN") eq "DE") {
|
||||||
(undef,undef,undef,$t{$i}) = ReadingsVal($name,"L4_NextHour".sprintf("%02d",$i)."_Time",'0') =~ m/(\d{2}).(\d{2}).(\d{4})\s(\d{2})/x;
|
(undef,undef,undef,$t{$i}) = ReadingsVal($name,"L4_NextHour".sprintf("%02d",$i)."_Time",'0') =~ m/(\d{2}).(\d{2}).(\d{4})\s(\d{2})/x;
|
||||||
@ -3010,7 +3035,8 @@ sub weather_icon {
|
|||||||
'170' => 'weather_night_snow_rain', # Mond, Wolke mit Schnee (1 Flocke) - Nacht # neu
|
'170' => 'weather_night_snow_rain', # Mond, Wolke mit Schnee (1 Flocke) - Nacht # neu
|
||||||
'171' => 'weather_night_snow_heavy', # Mond, Wolke mit Schnee (3 Flocken) - Nacht # neu
|
'171' => 'weather_night_snow_heavy', # Mond, Wolke mit Schnee (3 Flocken) - Nacht # neu
|
||||||
'180' => 'weather_night_thunderstorm_light', # Wolke mit Blitz - Nacht # neu
|
'180' => 'weather_night_thunderstorm_light', # Wolke mit Blitz - Nacht # neu
|
||||||
'181' => 'weather_night_thunderstorm' # Wolke mit Blitz und Starkregen - Nacht # neu
|
'181' => 'weather_night_thunderstorm', # Wolke mit Blitz und Starkregen - Nacht # neu
|
||||||
|
'999' => '1px-spacer' # Dummy - keine Anzeige Wettericon # vorhanden
|
||||||
);
|
);
|
||||||
|
|
||||||
return $weather_ids{$id} if(defined($weather_ids{$id}));
|
return $weather_ids{$id} if(defined($weather_ids{$id}));
|
||||||
|
@ -135,6 +135,7 @@ BEGIN {
|
|||||||
|
|
||||||
# Versions History intern
|
# Versions History intern
|
||||||
my %vNotesIntern = (
|
my %vNotesIntern = (
|
||||||
|
"2.10.3" => "11.06.2020 internal code changes, bug fixes show weather_icon ",
|
||||||
"2.10.2" => "10.06.2020 bug fixes get/switch consumers ",
|
"2.10.2" => "10.06.2020 bug fixes get/switch consumers ",
|
||||||
"2.10.1" => "08.06.2020 internal code changes, bug fixes ",
|
"2.10.1" => "08.06.2020 internal code changes, bug fixes ",
|
||||||
"2.10.0" => "03.06.2020 refactored login process ",
|
"2.10.0" => "03.06.2020 refactored login process ",
|
||||||
@ -212,6 +213,18 @@ my %statkeys = ( # Statistikdaten auszulesende Schlüs
|
|||||||
AutarkyRate => 1,
|
AutarkyRate => 1,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
# Tags der verfügbaren Datenquellen
|
||||||
|
my @pd = qw( balanceDayData
|
||||||
|
liveData
|
||||||
|
weatherData
|
||||||
|
forecastData
|
||||||
|
consumerLiveData
|
||||||
|
consumerDayData
|
||||||
|
consumerMonthData
|
||||||
|
consumerYearData
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
###############################################################
|
###############################################################
|
||||||
# SMAPortal Initialize
|
# SMAPortal Initialize
|
||||||
@ -219,6 +232,7 @@ my %statkeys = ( # Statistikdaten auszulesende Schlüs
|
|||||||
sub Initialize {
|
sub Initialize {
|
||||||
my ($hash) = @_;
|
my ($hash) = @_;
|
||||||
|
|
||||||
|
my $v5d = join ",", @pd;
|
||||||
$hash->{DefFn} = \&Define;
|
$hash->{DefFn} = \&Define;
|
||||||
$hash->{UndefFn} = \&Undefine;
|
$hash->{UndefFn} = \&Undefine;
|
||||||
$hash->{DeleteFn} = \&Delete;
|
$hash->{DeleteFn} = \&Delete;
|
||||||
@ -232,7 +246,7 @@ sub Initialize {
|
|||||||
"interval ".
|
"interval ".
|
||||||
"showPassInLog:1,0 ".
|
"showPassInLog:1,0 ".
|
||||||
"userAgent ".
|
"userAgent ".
|
||||||
"verbose5Data:none,loginData,balanceDayData,liveData,weatherData,forecastData,consumerLiveData,consumerDayData,consumerMonthData,consumerYearData ".
|
"verbose5Data:none,loginData,".$v5d." ".
|
||||||
$readingFnAttributes;
|
$readingFnAttributes;
|
||||||
|
|
||||||
eval { FHEM::Meta::InitMod( __FILE__, $hash ) }; ## no critic 'eval' # für Meta.pm (https://forum.fhem.de/index.php/topic,97589.0.html)
|
eval { FHEM::Meta::InitMod( __FILE__, $hash ) }; ## no critic 'eval' # für Meta.pm (https://forum.fhem.de/index.php/topic,97589.0.html)
|
||||||
@ -753,19 +767,17 @@ sub GetSetData { ## no cri
|
|||||||
my ($string) = @_;
|
my ($string) = @_;
|
||||||
my ($name,$getp,$setp) = split("\\|",$string);
|
my ($name,$getp,$setp) = split("\\|",$string);
|
||||||
my $hash = $defs{$name};
|
my $hash = $defs{$name};
|
||||||
my $errstate = 0;
|
|
||||||
my $useragent = AttrVal($name, "userAgent", "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; Trident/6.0)");
|
my $useragent = AttrVal($name, "userAgent", "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; Trident/6.0)");
|
||||||
my $cookieLocation = AttrVal($name, "cookieLocation", "./log/".$name."_cookie.txt");
|
my $cookieLocation = AttrVal($name, "cookieLocation", "./log/".$name."_cookie.txt");
|
||||||
my $v5d = AttrVal($name, "verbose5Data", "none");
|
my $v5d = AttrVal($name, "verbose5Data", "none");
|
||||||
my $dl = AttrVal($name, "detailLevel", 1); # selected Detail Level
|
my $dl = AttrVal($name, "detailLevel", 1); # selected Detail Level
|
||||||
my $state = "ok";
|
my $state = "ok";
|
||||||
my ($reread,$retry) = (0,0);
|
|
||||||
my ($exceed,$newcycle) = (0,0);
|
|
||||||
my ($st,$lc) = ("","");
|
my ($st,$lc) = ("","");
|
||||||
my @da = ();
|
my @da = ();
|
||||||
my ($ccdaydata_content,$ccmonthdata_content,$ccyeardata_content) = ("","","");
|
|
||||||
my ($d,$op,$paref);
|
|
||||||
|
|
||||||
|
my ($errstate,$reread,$retry,$exceed,$newcycle) = (0,0,0,0,0);
|
||||||
|
|
||||||
|
my ($d,$op);
|
||||||
if($setp ne "none") {
|
if($setp ne "none") {
|
||||||
# Verbraucher soll in den Status $op geschaltet werden
|
# Verbraucher soll in den Status $op geschaltet werden
|
||||||
($d,$op) = split(":",$setp);
|
($d,$op) = split(":",$setp);
|
||||||
@ -803,7 +815,7 @@ sub GetSetData { ## no cri
|
|||||||
|
|
||||||
### Login
|
### Login
|
||||||
##############
|
##############
|
||||||
$paref = [ $name, $ua, $state, $errstate ];
|
my $paref = [ $name, $ua, $state, $errstate ];
|
||||||
($state, $errstate) = _checkLogin ($paref);
|
($state, $errstate) = _checkLogin ($paref);
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
@ -854,16 +866,14 @@ sub GetSetData { ## no cri
|
|||||||
|
|
||||||
### Live-Daten
|
### Live-Daten
|
||||||
################
|
################
|
||||||
my ($livedata,$livedata_content) = _getData ({ name => $name,
|
($errstate,$state,$reread,$retry) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => 'https://www.sunnyportal.com/homemanager?t='.$time,
|
call => 'https://www.sunnyportal.com/homemanager?t='.$time,
|
||||||
tag => "liveData"
|
tag => "liveData",
|
||||||
});
|
|
||||||
|
|
||||||
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
|
||||||
errstate => $errstate,
|
|
||||||
state => $state,
|
state => $state,
|
||||||
data => $livedata
|
fnaref => [ qw( extractLiveData ) ],
|
||||||
|
addon => "",
|
||||||
|
daref => \@da
|
||||||
});
|
});
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
@ -899,36 +909,24 @@ sub GetSetData { ## no cri
|
|||||||
return "$name|$exceed|$newcycle|$errstate|$getp|$setp";
|
return "$name|$exceed|$newcycle|$errstate|$getp|$setp";
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($livedata_content && $livedata_content !~ m/undefined/ix) {
|
|
||||||
extractLiveData ($hash,\@da,$livedata_content);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
### Wetterdaten
|
### Wetterdaten
|
||||||
#####################
|
#####################
|
||||||
my ($weatherdata,$weatherdata_content) = _getData ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => 'https://www.sunnyportal.com/Dashboard/Weather',
|
call => 'https://www.sunnyportal.com/Dashboard/Weather',
|
||||||
tag => "weatherData"
|
tag => "weatherData",
|
||||||
});
|
|
||||||
|
|
||||||
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
|
||||||
errstate => $errstate,
|
|
||||||
state => $state,
|
state => $state,
|
||||||
data => $weatherdata
|
fnaref => [ qw( extractWeatherData ) ],
|
||||||
|
addon => "",
|
||||||
|
daref => \@da
|
||||||
});
|
});
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
$st = encode_base64 ( $state,"");
|
$st = encode_base64 ( $state,"");
|
||||||
return "$name|0|0|$errstate|$getp|$setp|$st";
|
return "$name|0|0|$errstate|$getp|$setp|$st";
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($weatherdata_content && $weatherdata_content !~ m/undefined/ix) {
|
|
||||||
extractWeatherData ($hash,\@da,$weatherdata_content);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@ -939,56 +937,40 @@ sub GetSetData { ## no cri
|
|||||||
my %fields = ("Content-Type" => "application/json; charset=utf-8");
|
my %fields = ("Content-Type" => "application/json; charset=utf-8");
|
||||||
my $cont = qq{ {"tabNumber":$tab,"anchorTime":$anchort} };
|
my $cont = qq{ {"tabNumber":$tab,"anchorTime":$anchort} };
|
||||||
|
|
||||||
my ($balancedataday,$balancedataday_content) = _putData ({ name => $name,
|
($errstate,$state) = _dispatchPost ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => 'https://www.sunnyportal.com/FixedPages/HoManEnergyRedesign.aspx/GetLegendWithValues',
|
call => 'https://www.sunnyportal.com/FixedPages/HoManEnergyRedesign.aspx/GetLegendWithValues',
|
||||||
|
tag => "balanceDayData",
|
||||||
|
state => $state,
|
||||||
|
fnaref => [ qw( extractStatisticData ) ],
|
||||||
fields => \%fields,
|
fields => \%fields,
|
||||||
content => $cont,
|
content => $cont,
|
||||||
tag => "balanceDayData"
|
addon => "Day",
|
||||||
|
daref => \@da
|
||||||
});
|
});
|
||||||
|
|
||||||
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
|
||||||
errstate => $errstate,
|
|
||||||
state => $state,
|
|
||||||
data => $balancedataday
|
|
||||||
});
|
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
$st = encode_base64 ( $state,"");
|
$st = encode_base64 ( $state,"");
|
||||||
return "$name|0|0|$errstate|$getp|$setp|$st";
|
return "$name|0|0|$errstate|$getp|$setp|$st";
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($balancedataday_content && $balancedataday_content !~ m/undefined/ix) {
|
|
||||||
extractStatisticData ($hash,\@da,$balancedataday_content,"Day");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
### Forecast Daten abrufen
|
### Forecast Daten abrufen
|
||||||
###########################
|
###########################
|
||||||
if($dl > 1) {
|
if($dl > 1) {
|
||||||
my ($forecastdata,$forecastdata_content) = _getData ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => 'https://www.sunnyportal.com/HoMan/Forecast/LoadRecommendationData',
|
call => 'https://www.sunnyportal.com/HoMan/Forecast/LoadRecommendationData',
|
||||||
tag => "forecastData"
|
tag => "forecastData",
|
||||||
});
|
|
||||||
|
|
||||||
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
|
||||||
errstate => $errstate,
|
|
||||||
state => $state,
|
state => $state,
|
||||||
data => $forecastdata
|
fnaref => [ qw( extractPlantData extractForecastData extractConsumerData ) ],
|
||||||
|
addon => "",
|
||||||
|
daref => \@da
|
||||||
});
|
});
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
$st = encode_base64 ($state, "");
|
$st = encode_base64 ( $state,"");
|
||||||
return "$name|0|0|$errstate|$getp|$setp|$st";
|
return "$name|0|0|$errstate|$getp|$setp|$st";
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($forecastdata_content && $forecastdata_content !~ m/undefined/ix) {
|
|
||||||
extractPlantData ($hash,\@da,$forecastdata_content);
|
|
||||||
extractForecastData ($hash,\@da,$forecastdata_content);
|
|
||||||
extractConsumerData ($hash,\@da,$forecastdata_content);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -997,27 +979,20 @@ sub GetSetData { ## no cri
|
|||||||
### Consumer Livedaten und historische Energiedaten
|
### Consumer Livedaten und historische Energiedaten
|
||||||
#####################################################
|
#####################################################
|
||||||
if($dl > 2) {
|
if($dl > 2) {
|
||||||
my ($consumerlivedata,$consumerlivedata_content) = _getData ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => 'https://www.sunnyportal.com/Homan/ConsumerBalance/GetLiveProxyValues',
|
call => 'https://www.sunnyportal.com/Homan/ConsumerBalance/GetLiveProxyValues',
|
||||||
tag => "consumerLiveData"
|
tag => "consumerLiveData",
|
||||||
});
|
|
||||||
|
|
||||||
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
|
||||||
errstate => $errstate,
|
|
||||||
state => $state,
|
state => $state,
|
||||||
data => $consumerlivedata
|
fnaref => [ qw( extractConsumerLiveData ) ],
|
||||||
|
addon => "",
|
||||||
|
daref => \@da
|
||||||
});
|
});
|
||||||
|
|
||||||
if($errstate) {
|
if($errstate) {
|
||||||
$st = encode_base64 ( $state,"");
|
$st = encode_base64 ( $state,"");
|
||||||
return "$name|0|0|$errstate|$getp|$setp|$st";
|
return "$name|0|0|$errstate|$getp|$setp|$st";
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($consumerlivedata_content && $consumerlivedata_content !~ m/undefined/ix) {
|
|
||||||
extractConsumerLiveData ($hash,\@da,$consumerlivedata_content);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
if($hash->{HELPER}{PLANTOID}) {
|
if($hash->{HELPER}{PLANTOID}) {
|
||||||
my $PlantOid = $hash->{HELPER}{PLANTOID};
|
my $PlantOid = $hash->{HELPER}{PLANTOID};
|
||||||
@ -1044,12 +1019,12 @@ sub GetSetData { ## no cri
|
|||||||
Log3 ($name, 4, "$name - Request date -> start: $dds, end: $dde");
|
Log3 ($name, 4, "$name - Request date -> start: $dds, end: $dde");
|
||||||
Log3 ($name, 5, "$name - Request consumer current day data string ->\n$ccdd");
|
Log3 ($name, 5, "$name - Request consumer current day data string ->\n$ccdd");
|
||||||
|
|
||||||
($errstate,$state) = _dispatch ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => $ccdd,
|
call => $ccdd,
|
||||||
tag => "consumerDayData",
|
tag => "consumerDayData",
|
||||||
state => $state,
|
state => $state,
|
||||||
function => "extractConsumerHistData",
|
fnaref => [ qw( extractConsumerHistData ) ],
|
||||||
addon => "day",
|
addon => "day",
|
||||||
daref => \@da
|
daref => \@da
|
||||||
});
|
});
|
||||||
@ -1063,12 +1038,12 @@ sub GetSetData { ## no cri
|
|||||||
Log3 ($name, 4, "$name - Request date -> start: $mds, end: $mde");
|
Log3 ($name, 4, "$name - Request date -> start: $mds, end: $mde");
|
||||||
Log3 ($name, 5, "$name - Request consumer current month data string ->\n$ccmd");
|
Log3 ($name, 5, "$name - Request consumer current month data string ->\n$ccmd");
|
||||||
|
|
||||||
($errstate,$state) = _dispatch ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => $ccmd,
|
call => $ccmd,
|
||||||
tag => "consumerMonthData",
|
tag => "consumerMonthData",
|
||||||
state => $state,
|
state => $state,
|
||||||
function => "extractConsumerHistData",
|
fnaref => [ qw( extractConsumerHistData ) ],
|
||||||
addon => "month",
|
addon => "month",
|
||||||
daref => \@da
|
daref => \@da
|
||||||
});
|
});
|
||||||
@ -1082,12 +1057,12 @@ sub GetSetData { ## no cri
|
|||||||
Log3 ($name, 4, "$name - Request date -> start: $yds, end: $yde");
|
Log3 ($name, 4, "$name - Request date -> start: $yds, end: $yde");
|
||||||
Log3 ($name, 5, "$name - Request consumer current year data string ->\n$ccyd");
|
Log3 ($name, 5, "$name - Request consumer current year data string ->\n$ccyd");
|
||||||
|
|
||||||
($errstate,$state) = _dispatch ({ name => $name,
|
($errstate,$state) = _dispatchGet ({ name => $name,
|
||||||
ua => $ua,
|
ua => $ua,
|
||||||
call => $ccyd,
|
call => $ccyd,
|
||||||
tag => "consumerYearData",
|
tag => "consumerYearData",
|
||||||
state => $state,
|
state => $state,
|
||||||
function => "extractConsumerHistData",
|
fnaref => [ qw( extractConsumerHistData ) ],
|
||||||
addon => "year",
|
addon => "year",
|
||||||
daref => \@da
|
daref => \@da
|
||||||
});
|
});
|
||||||
@ -1198,16 +1173,16 @@ return ($state, $errstate);
|
|||||||
}
|
}
|
||||||
|
|
||||||
################################################################
|
################################################################
|
||||||
# Dispatcher
|
# Dispatcher GET
|
||||||
################################################################
|
################################################################
|
||||||
sub _dispatch {
|
sub _dispatchGet {
|
||||||
my $paref = shift;
|
my $paref = shift;
|
||||||
my $name = $paref->{name};
|
my $name = $paref->{name};
|
||||||
my $ua = $paref->{ua}; # LWP Useragent
|
my $ua = $paref->{ua}; # LWP Useragent
|
||||||
my $call = $paref->{call}; # Seitenaufruf zur Datenquelle
|
my $call = $paref->{call}; # Seitenaufruf zur Datenquelle
|
||||||
my $tag = $paref->{tag}; # Kennzeichen der abzurufenen Daten
|
my $tag = $paref->{tag}; # Kennzeichen der abzurufenen Daten
|
||||||
my $state = $paref->{state};
|
my $state = $paref->{state};
|
||||||
my $fn = $paref->{function}; # aufzurufende Funktion zur Datenextraktion
|
my $fnref = $paref->{fnaref}; # Referenz zu Array der aufzurufenden Funktion(en) zur Datenextraktion
|
||||||
my $fnaddon = $paref->{addon}; # optionales Addon für aufzurufende Funktion
|
my $fnaddon = $paref->{addon}; # optionales Addon für aufzurufende Funktion
|
||||||
my $daref = $paref->{daref}; # Referenz zum Datenarray
|
my $daref = $paref->{daref}; # Referenz zum Datenarray
|
||||||
my $hash = $defs{$name};
|
my $hash = $defs{$name};
|
||||||
@ -1226,15 +1201,65 @@ sub _dispatch {
|
|||||||
data => $data
|
data => $data
|
||||||
});
|
});
|
||||||
|
|
||||||
return ($errstate,$state) if($errstate);
|
return ($errstate,$state,$reread,$retry) if($errstate || $reread || $retry);
|
||||||
|
|
||||||
if ($data_cont && $data_cont !~ m/undefined/ix) {
|
if ($data_cont && $data_cont !~ m/undefined/ix) {
|
||||||
|
my @func = @$fnref;
|
||||||
no strict "refs"; ## no critic 'NoStrict'
|
no strict "refs"; ## no critic 'NoStrict'
|
||||||
|
for my $fn (@func) {
|
||||||
&{$fn} ($hash,$daref,$data_cont,$fnaddon);
|
&{$fn} ($hash,$daref,$data_cont,$fnaddon);
|
||||||
|
}
|
||||||
use strict "refs";
|
use strict "refs";
|
||||||
}
|
}
|
||||||
|
|
||||||
return ($errstate,$state);
|
return ($errstate,$state,$reread,$retry);
|
||||||
|
}
|
||||||
|
|
||||||
|
################################################################
|
||||||
|
# Dispatcher POST
|
||||||
|
################################################################
|
||||||
|
sub _dispatchPost {
|
||||||
|
my $paref = shift;
|
||||||
|
my $name = $paref->{name};
|
||||||
|
my $ua = $paref->{ua}; # LWP Useragent
|
||||||
|
my $call = $paref->{call}; # Seitenaufruf zur Datenquelle
|
||||||
|
my $tag = $paref->{tag}; # Kennzeichen der abzurufenen Daten
|
||||||
|
my $state = $paref->{state};
|
||||||
|
my $fnref = $paref->{fnaref}; # Referenz zu Array der aufzurufenden Funktion(en) zur Datenextraktion
|
||||||
|
my $fields = $paref->{fields}; # Referenz zum Hash der zu übertragenden PUSH Header
|
||||||
|
my $cont = $paref->{content}; # Content Daten für PUSH (String)
|
||||||
|
my $fnaddon = $paref->{addon}; # optionales Addon für aufzurufende Funktion
|
||||||
|
my $daref = $paref->{daref}; # Referenz zum Datenarray
|
||||||
|
my $hash = $defs{$name};
|
||||||
|
|
||||||
|
my ($reread,$retry,$errstate) = (0,0,0);
|
||||||
|
|
||||||
|
my ($data,$data_cont) = _postData ({ name => $name,
|
||||||
|
ua => $ua,
|
||||||
|
call => $call,
|
||||||
|
tag => $tag,
|
||||||
|
fields => $fields,
|
||||||
|
content => $cont,
|
||||||
|
});
|
||||||
|
|
||||||
|
($reread,$retry,$errstate,$state) = _analyzeData ({ name => $name,
|
||||||
|
errstate => $errstate,
|
||||||
|
state => $state,
|
||||||
|
data => $data
|
||||||
|
});
|
||||||
|
|
||||||
|
return ($errstate,$state) if($errstate);
|
||||||
|
|
||||||
|
if ($data_cont && $data_cont !~ m/undefined/ix) {
|
||||||
|
my @func = @$fnref;
|
||||||
|
no strict "refs"; ## no critic 'NoStrict'
|
||||||
|
for my $fn (@func) {
|
||||||
|
&{$fn} ($hash,$daref,$data_cont,$fnaddon);
|
||||||
|
}
|
||||||
|
use strict "refs";
|
||||||
|
}
|
||||||
|
|
||||||
|
return ($errstate,$state,$reread,$retry);
|
||||||
}
|
}
|
||||||
|
|
||||||
################################################################
|
################################################################
|
||||||
@ -1268,7 +1293,7 @@ return ($data,$dcont);
|
|||||||
################################################################
|
################################################################
|
||||||
# Standard Abruf Daten POST
|
# Standard Abruf Daten POST
|
||||||
################################################################
|
################################################################
|
||||||
sub _putData {
|
sub _postData {
|
||||||
my $paref = shift;
|
my $paref = shift;
|
||||||
my $name = $paref->{name};
|
my $name = $paref->{name};
|
||||||
my $ua = $paref->{ua};
|
my $ua = $paref->{ua};
|
||||||
@ -1692,7 +1717,7 @@ sub extractForecastData { ## no critic 'complexity'
|
|||||||
push @$daref, "L4_${time_str}_Total:". (int($fc_obj->{'PvMeanPower'}->{'Amount'}) - int($fc_obj->{'ConsumptionForecast'}->{'Amount'} / 3600))." Wh";
|
push @$daref, "L4_${time_str}_Total:". (int($fc_obj->{'PvMeanPower'}->{'Amount'}) - int($fc_obj->{'ConsumptionForecast'}->{'Amount'} / 3600))." Wh";
|
||||||
|
|
||||||
# add WeatherId Helper to show weather icon
|
# add WeatherId Helper to show weather icon
|
||||||
$hash->{HELPER}{"L4_".${time_str}."_WeatherId"} = int($fc_obj->{'WeatherId'}) if(defined $fc_obj->{'WeatherId'});
|
BlockingInformParent("FHEM::SMAPortal::setFromBlocking", [$name, "NULL", "L4_".${time_str}."_WeatherId:".int($fc_obj->{'WeatherId'}) ], 1) if(defined $fc_obj->{'WeatherId'});
|
||||||
}
|
}
|
||||||
if($time_str =~ /ThisHour/x && $dl >= 2) {
|
if($time_str =~ /ThisHour/x && $dl >= 2) {
|
||||||
push @$daref, "L2_${time_str}_Time:". TimeAdjust($hash,$fc_obj->{'TimeStamp'}->{'DateTime'},$tkind);
|
push @$daref, "L2_${time_str}_Time:". TimeAdjust($hash,$fc_obj->{'TimeStamp'}->{'DateTime'},$tkind);
|
||||||
@ -1702,7 +1727,7 @@ sub extractForecastData { ## no critic 'complexity'
|
|||||||
push @$daref, "L2_${time_str}_Total:". (int($fc_obj->{'PvMeanPower'}->{'Amount'}) - int($fc_obj->{'ConsumptionForecast'}->{'Amount'} / 3600))." Wh";
|
push @$daref, "L2_${time_str}_Total:". (int($fc_obj->{'PvMeanPower'}->{'Amount'}) - int($fc_obj->{'ConsumptionForecast'}->{'Amount'} / 3600))." Wh";
|
||||||
|
|
||||||
# add WeatherId Helper to show weather icon
|
# add WeatherId Helper to show weather icon
|
||||||
$hash->{HELPER}{"L2_".${time_str}."_WeatherId"} = int($fc_obj->{'WeatherId'}) if(defined $fc_obj->{'WeatherId'});
|
BlockingInformParent("FHEM::SMAPortal::setFromBlocking", [$name, "NULL", "L2_".${time_str}."_WeatherId:".int($fc_obj->{'WeatherId'}) ], 1) if(defined $fc_obj->{'WeatherId'});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -2485,7 +2510,7 @@ sub PortalAsHtml {
|
|||||||
$di{0} = $pv{0} - $co{0};
|
$di{0} = $pv{0} - $co{0};
|
||||||
$is{0} = (ReadingsVal($name,"L2_ThisHour_IsConsumptionRecommended",'no') eq 'yes' ) ? $icon : undef;
|
$is{0} = (ReadingsVal($name,"L2_ThisHour_IsConsumptionRecommended",'no') eq 'yes' ) ? $icon : undef;
|
||||||
$we{0} = $hash->{HELPER}{L2_ThisHour_WeatherId} if($weather); # für Wettericons
|
$we{0} = $hash->{HELPER}{L2_ThisHour_WeatherId} if($weather); # für Wettericons
|
||||||
$we{0} = $we{0}?$we{0}:0;
|
$we{0} = $we{0} ? $we{0} : 999;
|
||||||
|
|
||||||
if(AttrVal("global","language","EN") eq "DE") {
|
if(AttrVal("global","language","EN") eq "DE") {
|
||||||
(undef,undef,undef,$t{0}) = ReadingsVal($name,"L2_ThisHour_Time",'0') =~ m/(\d{2}).(\d{2}).(\d{4})\s(\d{2})/x;
|
(undef,undef,undef,$t{0}) = ReadingsVal($name,"L2_ThisHour_Time",'0') =~ m/(\d{2}).(\d{2}).(\d{4})\s(\d{2})/x;
|
||||||
@ -2558,7 +2583,7 @@ sub PortalAsHtml {
|
|||||||
|
|
||||||
$is{$i} = (ReadingsVal($name,"L4_NextHour".sprintf("%02d",$i)."_IsConsumptionRecommended",'no') eq 'yes') ? $icon : undef;
|
$is{$i} = (ReadingsVal($name,"L4_NextHour".sprintf("%02d",$i)."_IsConsumptionRecommended",'no') eq 'yes') ? $icon : undef;
|
||||||
$we{$i} = $hash->{HELPER}{"L4_NextHour".sprintf("%02d",$i)."_WeatherId"} if($weather); # für Wettericons
|
$we{$i} = $hash->{HELPER}{"L4_NextHour".sprintf("%02d",$i)."_WeatherId"} if($weather); # für Wettericons
|
||||||
$we{$i} = $we{$i}?$we{$i}:0;
|
$we{$i} = $we{$i} ? $we{$i} : 999;
|
||||||
|
|
||||||
if(AttrVal("global","language","EN") eq "DE") {
|
if(AttrVal("global","language","EN") eq "DE") {
|
||||||
(undef,undef,undef,$t{$i}) = ReadingsVal($name,"L4_NextHour".sprintf("%02d",$i)."_Time",'0') =~ m/(\d{2}).(\d{2}).(\d{4})\s(\d{2})/x;
|
(undef,undef,undef,$t{$i}) = ReadingsVal($name,"L4_NextHour".sprintf("%02d",$i)."_Time",'0') =~ m/(\d{2}).(\d{2}).(\d{4})\s(\d{2})/x;
|
||||||
@ -3010,7 +3035,8 @@ sub weather_icon {
|
|||||||
'170' => 'weather_night_snow_rain', # Mond, Wolke mit Schnee (1 Flocke) - Nacht # neu
|
'170' => 'weather_night_snow_rain', # Mond, Wolke mit Schnee (1 Flocke) - Nacht # neu
|
||||||
'171' => 'weather_night_snow_heavy', # Mond, Wolke mit Schnee (3 Flocken) - Nacht # neu
|
'171' => 'weather_night_snow_heavy', # Mond, Wolke mit Schnee (3 Flocken) - Nacht # neu
|
||||||
'180' => 'weather_night_thunderstorm_light', # Wolke mit Blitz - Nacht # neu
|
'180' => 'weather_night_thunderstorm_light', # Wolke mit Blitz - Nacht # neu
|
||||||
'181' => 'weather_night_thunderstorm' # Wolke mit Blitz und Starkregen - Nacht # neu
|
'181' => 'weather_night_thunderstorm', # Wolke mit Blitz und Starkregen - Nacht # neu
|
||||||
|
'999' => '1px-spacer' # Dummy - keine Anzeige Wettericon # vorhanden
|
||||||
);
|
);
|
||||||
|
|
||||||
return $weather_ids{$id} if(defined($weather_ids{$id}));
|
return $weather_ids{$id} if(defined($weather_ids{$id}));
|
||||||
|
Loading…
x
Reference in New Issue
Block a user