Neue Version von HTTPMOD mit neuen Features zum Testen

Begonnen von StefanStrobel, 05 Dezember 2015, 08:31:32

Vorheriges Thema - Nächstes Thema

andyclimb

Is there a reason that

Zitat
# No cyclic requests and no main URL needed in this example
define MyDevice none 0

attr MyDevice set01Name Licht
attr MyDevice set01URL http://192.168.1.22/switch=$val
A user command

set MyDevice Licht 1
will be translated into the http GET request

http://192.168.1.22/switch=1
In this example a map would also be helpful, that translates on / off to 0 or 1 and allows the user to select on/of in fhemweb:

attr MyDevive set01IMap 0:off, 1:on

$val MUST be a number.  I'd like to send get requests.... x = y and they are all strings.  seems really strange to me that you can't have


attr MyDevice set01URL http://192.168.1.22/$1=$2


where

set MyDevice Licht mode Adalight 

which would give you the get request

attr MyDevice set01URL http://192.168.1.22/mode=Adalight


Any reason why it can only be 1, and has to be a number?
AM

Burny4600

#136
Kann mir jemand bei meiner Datenlogger Web 2 Anbindung helfen.
Ich blicke da nicht ganz durch wie ich die Daten vernünftig aus dem Fronius IG20 bekomme.
Habe schon einiges getestet.
Daten werden zwar in den buf eingelesen aber da stehe ich dann an.
Nun bekomme ich auch noch diese Meldung gelegentlich.
Messages collected while initializing FHEM:
configfile: Please install JSON Library to use JSON (apt-get install libjson-perl) - error was Can't locate JSON.pm in @INC (you may need to install the JSON module) (@INC contains: /etc/perl /usr/local/lib/arm-linux-gnueabihf/perl/5.20.2 /usr/local/share/perl/5.20.2 /usr/lib/arm-linux-gnueabihf/perl5/5.20 /usr/share/perl5 /usr/lib/arm-linux-gnueabihf/perl/5.20 /usr/share/perl/5.20 /usr/local/lib/site_perl . ./FHEM) at (eval 13) line 2, <$fh> line 9.
BEGIN failed--compilation aborted at (eval 13) line 2, <$fh> line 9.

Habe jedenfalls die Nachinstallation durchgeführt.
sudo apt-get install libjson-perl
Trotzdem funktioniert das ganze nicht nach einem Reboot.

Die Konfiguration sieht so aus:

# Fronius Eingangsdaten JSON PV-Anlagen
define PV_Anlage HTTPMOD none 60
attr PV_Anlage userattr get01Name getHeader1 getHeader2 getURL
attr PV_Anlage extractAllJSON 1
attr PV_Anlage get01Name Fronius_Daten
attr PV_Anlage getHeader1 Content-Type: application/json
attr PV_Anlage getHeader2 Accept: */*
attr PV_Anlage getURL http://192.xxx.xxx.xxx/solar_api/GetInverterRealtimeData.cgi?Scope=System

# Fronius Eingangsdaten PV-Anlagen 1
define PV_Anlage_1 HTTPMOD http://192.xxx.xxx.xxx/solar_api/GetInverterRealtimeData.cgi?Scope=System 60
attr PV_Anlage_1 userattr reading01Name reading01Regex reading02Name reading02Regex reading03Name reading03Regex reading04Name reading04Regex reading05Name reading05Regex reading06Name reading06Regex reading07Name reading07Regex reading07ame reading08Name reading08Regex reading09Name reading09Regex
attr PV_Anlage_1 reading01Name DAY_ENERGY
attr PV_Anlage_1 reading01Regex "DAY_ENERGY"[:{\n\t]+"Value"[:\t]+([\d\.]+),
attr PV_Anlage_1 reading02Name TOTAL_ENERGY
attr PV_Anlage_1 reading02Regex "TOTAL_ENERGY"[:{\n\t ]+"Value"[ : \t]+([\d\.]+),
attr PV_Anlage_1 reading03Name YEAR_ENERGY
attr PV_Anlage_1 reading03Regex "YEAR_ENERGY"[:{\n\t ]+"Value"[ : \t]+([\d\.]+),
attr PV_Anlage_1 reading04Name FAC
attr PV_Anlage_1 reading04Regex "FAC"[:{\n\t ]+"Value"[ : \t]+([\d\.]+),
attr PV_Anlage_1 reading05Name IAC
attr PV_Anlage_1 reading05Regex "IAC"[:{\n\t ]+"Value"[ : \t]+([\d\.]+),
attr PV_Anlage_1 reading06Name IDC
attr PV_Anlage_1 reading06Regex "IDC"[:{\n\t ]+"Value"[ : \t]+([\d\.]+),
attr PV_Anlage_1 reading07Name PAC
attr PV_Anlage_1 reading07Regex "PAC"[:{\n\t ]+"Value"[ : \t]+([\d\.]+),
attr PV_Anlage_1 reading08Name UAC
attr PV_Anlage_1 reading08Regex "UAC"[:{\n\t ]+"Value"[ : \t]+([\d\.]+),
attr PV_Anlage_1 reading09Name UDC
attr PV_Anlage_1 reading09Regex "UDC"[:{\n\t ]+"Value"[ : \t]+([\d\.]+),
attr PV_Anlage_1 stateFormat {sprintf("%d", ReadingsVal($name,"PAC",0))}
attr PV_Anlage_1 userReadings PAC
attr PV_Anlage_1 verbose 2


Mit der Datenanforderung bekomme ich Daten in der Form:
http://192.xxx.xxx.xxx/solar_api/GetInverterRealtimeData.cgi?Scope=System
{
"Head" : {
"RequestArguments" : {
"Scope" : "System"
},
"Status" : {
"Code" : 0,
"Reason" : "",
"UserMessage" : ""
},
"Timestamp" : "2016-03-24T07:08:27+01:00"
},
"Body" : {
"Data" : {
"PAC" : {
"Unit" : "W",
"Values" : {
"1" : 41
}
},
"DAY_ENERGY" : {
"Unit" : "Wh",
"Values" : {
"1" : 0
}
},
"YEAR_ENERGY" : {
"Unit" : "Wh",
"Values" : {
"1" : 243000
}
},
"TOTAL_ENERGY" : {
"Unit" : "Wh",
"Values" : {
"1" : 19942000
}
}
}
}
}



Mfg Chris

Raspberry Pi 2/2+/3/3+/4 / Betriebssystem: Bullseye Lite
Schnittstellen: RFXtrx433E, SIGNALduino, MQTT, nanoCUL, HM-MOD-UART, 1-Wire, LAN, ser2net, FHEM2FEHEM
Devices: S.USV, APC-USV, Fronius Datalogger Web 2, FS20, IT, Resol VBUS & DL2, TEK603, WMR200, YouLess, Homematic, MQTT

HotteFred

Zitat von: StefanStrobel am 23 März 2016, 15:07:40
Du kannst mehrere gets definieren und jedes get kann seine eigene URL haben, z.B. get01URL, get02URL etc.

Hallo Stefan,

ja, genau so möchte ich es.

Danke und Grüße
BananaPi mit FHEM, KM50, Velux Raumluftsensor, jede Menge HM-CC-RT-DN, jede Menge 1Wire Zeugs

StefanStrobel

Hallo andyclimb,

Parameters to set commands can be text if you set the attribute set01TextArg to 1.

To get started with JSON parsing I would use ExtractAllJSON first. It creates a reading for every key and then you can refine your configuration and limit the extraction to the key you want by specifying reading01JSON or get01JSON.

The wiki contains more examples and explanations.

Regards,
     Stefan

StefanStrobel

Hallo Chris,

Wenn Perl die JSON Library nicht laden kann, ist die offenbar nicht korrekt / vollständig installiert.
Hast du im Perl INC-Pfad mal nach JSON.pm gesucht? Gab es bei der Installation irgendwelche Fehlermeldungen?

Das ganze ist auf jeden Fall kein großes Problem. Der JSON Parser ist zwar für manche Fälle eleganter, aber mit Regexes kann man alles auch machen.

Für Deinen PAC-Wert sollte z.B. PAC[^\:]+:[^\:]+:[^\:]+:[^\:]+: ([\d\.]+) Funktionieren.

Wenn es mit Zeilenumbrüchen und Strings zwischen dem relevanten Key und dem gesuchten Wert zu kompliziert wird, hilft es oft wenn man die regex negativ formuliert. Im obigen Beispiel ist das 4 mal "kein Doppelpunkt" und dann ein Doppelpunkt ...

Gruß
     Stefan

andyclimb

stefan.

Thanks for the help.  That worked great!!!  thank you.  Is there a way to have more than one argument?

I have ExtractAllJSON, and it works for everything, except where there is an array of strings.  it will extract an array of key value pairs, but not strings into a single reading...
AM

Burny4600

Habe sudo apt-get install libjson-perl nochmals ausgeführt und neu gestartet.

Scheint jetzt zu funktionieren.
Mfg Chris

Raspberry Pi 2/2+/3/3+/4 / Betriebssystem: Bullseye Lite
Schnittstellen: RFXtrx433E, SIGNALduino, MQTT, nanoCUL, HM-MOD-UART, 1-Wire, LAN, ser2net, FHEM2FEHEM
Devices: S.USV, APC-USV, Fronius Datalogger Web 2, FS20, IT, Resol VBUS & DL2, TEK603, WMR200, YouLess, Homematic, MQTT

StefanStrobel

Hello andyclimb,

If you pass a string this could of course be something like x=y. If you need more flexibility you can use user defined replacements in HTTPMOD. Then you can put as many variables / values in URLs, headers or post data as you like.

The problem with arrays of strings is a bug. I'm currently testing a fix however so far it creates individual readings for each element. My plan is to allow to recombine these elements into one reading with a recombineExpr as it works for regex and xpath already.
I'll probably post a version for testing in the next days.

Regards,
    Stefan

StefanStrobel

#143
Hello andyclimb,

can you please test the attached new Version of HTTPMOD?
It should now also extract arrays of strings.

To get one single reading with thelist of modes you need to define

attr MyDevice reading01Name ModesList
attr MyDevice reading01JSON modes
attr MyDevice reading01RecombineExpr join ",", @matchlist

This will cause a new reading called ModesList to be created. It will be a comma seperated list of all json objects that start with modes.


regards,
    Stefan

EDIT: 28.3.16 - neuere Version im nächsten Post

StefanStrobel

Hier nochmal eine neue Version mit einem Fix für das Cookie-Handling.

Gruss
    Stefan

pejonp

#145
Hallo Stefan,

ich möchte diese XML Daten auslesen und als Reading darstellen. Klappt aber nicht. Hier meine Definitionen.


define SB HTTPMOD http://Ip:3480/data_request?id=status&output_format=xml 60
attr SB userattr reading01Name reading01XPath-Strict reading02Name reading02XPath reading02XPath-Strict reading03Name reading03XPath-Strict reading04Name reading04XPath-Strict requestHeader1
attr SB enableXPath-Strict 1
attr SB event-on-change-reading .*
attr SB group SB
attr SB reading01Name devices
attr SB reading01XPath-Strict //devices/text()
attr SB reading02Name states
attr SB reading02XPath-Strict //states/text()
attr SB reading03Name devices-1
attr SB reading03XPath-Strict //devices-1/text()
attr SB reading04Name categories
attr SB reading04XPath-Strict //categories/text()
attr SB room SB
attr SB verbose 5
define FileLog_SB1 FileLog ./log/SB1-%Y-%m.log  SB
attr FileLog_SB1 logtype text
attr FileLog_SB1 room Haus


Es werden diese Readings angelegt und mehr passiert nicht. Was muss ich anders machen ? Vielen Dank.

devices-1        2016-04-03 20:58:22

Jörg
LaCrossGW 868MHz:WT470+TFA+TX37-IT+EMT7110+W136+WH25A HP1003+WH2621
SignalD(CC1101):Bresser+WS-0101(868MHz WH1080)+Velux KLF200+MAX!+HM-MOD-UART:Smoke HM-SEC-SD+VITOSOLIC 200 RESOL VBUS-LAN+SolarEdge SE5K(Modbus)+Sonnen!eco8(10kWh)+TD3511+DRT710M(Modbus)+ZigBee+Z-Wave+MQTT+vitoconnect

frank

#146
hallo stefan,

ich habe ein zyklisches httpmod device mit zwei get auf unterschiedliche url's, die quasi gemeinsam abgeholt werden.
dabei gibt es kleine wünsche/probleme.

1. MATCHED_READINGS
hier wird das ergebnis jedes einzelnen get getrennt ausgegeben. am ende des kompletten durchlaufs stehen hier leider nur die readings des letzten get aufrufs.
da ich am ende der gesamtem prozedur ein userreadings triggern möchte und die namen aller erzeugten readings benötige, wäre es schön, wenn hier das gesamtergebnis enthalten wäre.

2. probleme mit event-on-change
ich habe "event-on-change-reading .*" gesetzt, also auf alles. das scheint für das 2. get nicht zu wirken. obwohl die readings immer gleich bleiben, werden trotzdem für alle readings events erzeugt.

3. getXXOExpr
hier funktioniert leider keine substitution wie zb
$val =~ s/^([^_]+)([^-]+)(..)(.*)$/$1.$3.$2.$4/
bei erfolg wird $val=1 gesetzt, sonst nichts. kann man das reparieren, oder muss ich das anders schreiben? ersatzweise funktioniert aber zb sowas:
($val=~m/^([^_]+)([^-]+)(..)(.*)$/)?($1.$3.$2.$4):"error"

edit:

4. MaxAge...
für jedes get habe ich getXXMaxAge=10 und getXXMaxAgeReplacementMode=delete separat definiert.
nun verhält es sich so, dass bei jedem einzelnen request alle readings geprüft und ggf gelöscht werden und nicht nur die readings des korrespondierenden requests. das hat zur folge, dass wenn ich einen manuellen get befehl auf einen einzelnen request ausführe, die readings des zweiten get gelöscht werden.
ist das so gewollt, oder könnte man die prüfung auf die zum get korrespondierenden readings beschränken?

gruss frank
FHEM: 6.0(SVN) => Pi3(buster)
IO: CUL433|CUL868|HMLAN|HMUSB2|HMUART
CUL_HM: CC-TC|CC-VD|SEC-SD|SEC-SC|SEC-RHS|Sw1PBU-FM|Sw1-FM|Dim1TPBU-FM|Dim1T-FM|ES-PMSw1-Pl
IT: ITZ500|ITT1500|ITR1500|GRR3500
WebUI [HMdeviceTools.js (hm.js)]: https://forum.fhem.de/index.php/topic,106959.0.html

StefanStrobel

Hallo Jörg,

bei solchen Problemen liegt es meistens am angegebenen XPath.
Leider bin ich da auch nicht der absolute XPath-Experte. Mit ein bischen Rumprobieren bekommt man es aber meistens hin. Vielleicht liest ja jemand mit, der tiefer im XML / XPath Thema drinsteckt und sich das File mal genauer ansehen kann?

Gruss
    Stefan

StefanStrobel

Hallo Frank,

zu 4) Das ist so gewollt. Wenn MaxAge 10 gesetzt ist und der Wert schon älter als 10 Sekunden ist, dann wird die Reaktion getriggert, sobald das Modul eine Chance dazu hat (ohne viele weitere InternalTimer zu setzen) - also auch beim nächsten Get für andere Werte.
Der MaxAge Wert sollte daher so groß sein, dass er nur greift wenn die übliche Aktualisierung schon gelaufen ist.

zu 3)
$val wird der OExpr nur zum Lesen bereitgestellt. Das Ergebnis der Expression wird dann weiterverwendet.

zu 1) sollte machbar sein. Schau ich mir an.
zu 2) das muss ich mir noch genauer ansehen. Wird eine Weile dauern.

Gruss
    Stefan

frank

#149
Zitat von: StefanStrobel am 05 April 2016, 16:49:13
zu 4) Das ist so gewollt. Wenn MaxAge 10 gesetzt ist und der Wert schon älter als 10 Sekunden ist, dann wird die Reaktion getriggert, sobald das Modul eine Chance dazu hat (ohne viele weitere InternalTimer zu setzen) - also auch beim nächsten Get für andere Werte.
Der MaxAge Wert sollte daher so groß sein, dass er nur greift wenn die übliche Aktualisierung schon gelaufen ist.
ok, dann muss ich mir etwas anderes überlegen.
denn eigentlich benötige ich keine zeitabhängige löschung, sondern eine löschung eventuell noch vorhandener daten des letzten requests, aber nur, wenn der aktuelle request erfolgreich war. da die anzahl der readings eines aktuellen request kleiner sein kann, als die anzahl des alten requests, würden in diesem fall ein paar alte und damit ungültige readings erhalten bleiben. ich arbeite jeweils mit regex und regexopt=g. ausserdem müsste das für jedes get separat funktionieren.

mal sehen, was du bei matched_readings zauberst.

edit:
Zitatzu 2) das muss ich mir noch genauer ansehen. Wird eine Weile dauern.
nachdem ich nun alle maxage attribute entfernt habe, funktioniert event-on-change scheinbar problemlos. also entwarnung.

gruss frank

FHEM: 6.0(SVN) => Pi3(buster)
IO: CUL433|CUL868|HMLAN|HMUSB2|HMUART
CUL_HM: CC-TC|CC-VD|SEC-SD|SEC-SC|SEC-RHS|Sw1PBU-FM|Sw1-FM|Dim1TPBU-FM|Dim1T-FM|ES-PMSw1-Pl
IT: ITZ500|ITT1500|ITR1500|GRR3500
WebUI [HMdeviceTools.js (hm.js)]: https://forum.fhem.de/index.php/topic,106959.0.html