Hallo zusammen,
ich möchte einem MAX Thermostat ein userReading mit der Temperatur übergeben, wenn die valveposition > 50% ist. Hintergrund ist, dass ich damit dann kurzzeitig die Temperatur senken will und 3 Minuten später wieder auf diesen gespeicherten Wert zurück möchte und somit eine Aktualisierung der gemessenen Temperatur erzwingen möchte. Dazu habe ich ein DOIF, das seinen Wert bei > 50% mit einer Wartezeit von 5400 Sekunden sein state ändert und dann eine sub aufruft mit den Befehlen zum senken und wieder zurückstellen der Temperatur. Das funktioniert soweit prima, was aber nicht funktioniert ist das userReading korrekt einzutragen. Es steht genau immer das Gegenteil von dem drin, was drin stehen soll. Also bei cmd_2 des DOIF wird die Temperatur eingetragen, bei cmd_1 ist das Reading leer.
attr EG_Bad_T usr_Temp { if(ReadingsVal("Gaesteklo_ValveScanner_DI","state","") eq "cmd_1") {return (ReadingsVal("EG_Bad_T","desiredTemperature","7.5"))} }
Wo ist der Denkfehler??
Zitat von: persching am 01 November 2019, 10:14:45
attr EG_Bad_T usr_Temp {
kann nicht sein , bitte list posten und zwar von beiden Geräten
Dieser Code stammt aus einem (abgewandelten) Beispiel aus https://wiki.fhem.de/wiki/UserReadings (https://wiki.fhem.de/wiki/UserReadings). Dort steht dann:
Zitat
Ausgabe eines Homematic 3-State Fenstersensor als Zahl für Visualisierung mit Icons
attr HM_XXXXXX userReadings Statenum {if(ReadingsVal("HM_XXXXXX","state","") eq "closed") {return 0} elsif (ReadingsVal("HM_XXXXXX","state","") eq "tilted") {return 1} elsif (ReadingsVal("HM_XXXXXX","state","") eq "open") {return 2} else {return -1}}
Aber hier sind die Listings:
Internals:
DEF HeatingThermostat 075a93
FUUID 5c49a04b-f33f-e65d-8f65-d97a4fe081d08222
IODev cm
LASTInputDev cm
MSGCNT 495
NAME EG_Bad_T
NR 32
RSSI -73
STATE 21.5 °C
STILLDONETIME 0
TYPE MAX
addr 075a93
backend cm
cm_MSGCNT 495
cm_TIME 2019-11-01 10:32:28
dstsetting 1
mode 1
rferror 0
type HeatingThermostat
Helper:
DBLOG:
RSSI:
logdb:
TIME 1572600748.63927
VALUE -73
desiredTemperature:
logdb:
TIME 1572600748.63927
VALUE 21.5
temperature:
logdb:
TIME 1572600748.63927
VALUE 23.0
valveposition:
logdb:
TIME 1572600748.63927
VALUE 18
OLDREADINGS:
2019-11-01 09:18:28 desiredTemperature 22.0
READINGS:
2019-11-01 10:32:28 RSSI -73
2016-06-15 20:20:59 TimeInformationHour 0
2019-11-01 10:32:28 battery ok
2019-11-01 10:32:28 batteryState ok
2016-06-15 21:19:42 comfortTemperature 21
2019-11-01 10:32:28 desiredTemperature 21.5
2016-06-15 21:19:42 ecoTemperature 17
2018-12-28 21:46:34 firmware 1.8
2018-12-28 21:46:34 groupid 0
2016-06-15 21:19:42 maximumTemperature on
2016-06-15 21:19:44 measurementOffset 1.0
2016-06-15 21:19:42 minimumTemperature off
2019-11-01 10:32:28 mode manual
2019-11-01 09:55:30 msgcnt 58
2019-11-01 10:32:28 panel unlocked
2019-11-01 10:32:28 state 21.5 °C
2019-11-01 10:32:28 temperature 23.0
2018-12-28 21:46:34 testresult 255
2019-11-01 10:32:28 usr_Temp
2019-11-01 10:32:28 valveposition 18
2019-10-31 15:34:28 watchShutter EG_Bad_Fensterkontakt
2016-06-15 21:19:42 windowOpenDuration 15
2016-06-15 21:19:42 windowOpenTemperature 12
internals:
interfaces thermostat;battery;temperature
Attributes:
IODev cm
event-on-change-reading valveposition,desiredTemperature,temperature,battery,RSSI
event-on-update-reading valveposition,desiredTemperature,temperature
group Heizung
icon temp_control
mqttName Thermostat
mqttRoom Gaesteklo
oldreadings desiredTemperature
room Erdgeschoss->Gästeklo,Heizung->Thermostate,System->Schnittstellen->MAX
scanTemp 0
userReadings usr_Temp { if(ReadingsVal("Gaesteklo_ValveScanner_DI","state","") eq "cmd_1") {return (ReadingsVal("EG_Bad_T","desiredTemperature","7.5"))} }
userattr MAX MAX_map structexclude
verbose 5
Internals:
DEF ([EG_Bad_T:valveposition] > 30) ({ SetResetThermostat("EG_Bad_T") })
FUUID 5dbaf274-f33f-e65d-a502-ec71dc662d77ed1a
MODEL FHEM
NAME Gaesteklo_ValveScanner_DI
NOTIFYDEV global,EG_Bad_T
NR 50264
NTFY_ORDER 50-Gaesteklo_ValveScanner_DI
STATE cmd_2
TYPE DOIF
VERSION 20268 2019-09-28 21:00:39
Helper:
DBLOG:
cmd:
logdb:
TIME 1572595348.45472
VALUE 1
cmd_event:
logdb:
TIME 1572595348.45472
VALUE EG_Bad_T
cmd_nr:
logdb:
TIME 1572595348.45472
VALUE 1
mode:
logdb:
TIME 1572546294.17343
VALUE enabled
state:
logdb:
TIME 1572595348.45472
VALUE cmd_1
wait_timer:
logdb:
TIME 1572595348.42498
VALUE no timer
warning:
logdb:
TIME 1572532979.65959
VALUE condition c01
READINGS:
2019-11-01 10:32:28 Device EG_Bad_T
2019-11-01 09:58:28 cmd 2
2019-11-01 09:58:28 cmd_event EG_Bad_T
2019-11-01 09:58:28 cmd_nr 2
2019-11-01 10:32:28 e_EG_Bad_T_valveposition 18
2019-10-31 19:24:54 mode enabled
2019-11-01 09:58:28 state cmd_2
2019-11-01 09:20:28 wait_timer no timer
Regex:
accu:
cond:
EG_Bad_T:
0:
valveposition ^EG_Bad_T$:^valveposition:
attr:
cmdState:
wait:
0:
120
waitdel:
condition:
0 ::ReadingValDoIf($hash,'EG_Bad_T','valveposition') > 30
do:
0:
0 { SetResetThermostat("EG_Bad_T") }
1:
helper:
DEVFILTER ^global$|^EG_Bad_T$
NOTIFYDEV global|EG_Bad_T
event desiredTemperature: 21.5,temperature: 23.0,valveposition: 18,RSSI: -73
globalinit 1
last_timer 0
sleepdevice EG_Bad_T
sleepsubtimer -1
sleeptimer -1
timerdev EG_Bad_T
timerevent desiredTemperature: 21.5,temperature: 23.0,valveposition: 18,RSSI: -73
triggerDev EG_Bad_T
timerevents:
desiredTemperature: 21.5
temperature: 23.0
valveposition: 18
RSSI: -73
timereventsState:
desiredTemperature: 21.5
temperature: 23.0
valveposition: 18
RSSI: -73
triggerEvents:
desiredTemperature: 21.5
temperature: 23.0
valveposition: 18
RSSI: -73
triggerEventsState:
desiredTemperature: 21.5
temperature: 23.0
valveposition: 18
RSSI: -73
internals:
readings:
all EG_Bad_T:valveposition
trigger:
uiState:
uiTable:
Attributes:
DbLogExclude .*
event-on-change-reading state
room Roomdetails->Gästeklo
wait 120
Ich hab es jetzt auf anderem Weg gelöst und jetzt funktioniert es:
attr EG_Bad_T userReadings usr_Temp { if(ReadingsVal("EG_Bad_T","valveposition","0") > 50) {return (ReadingsVal("EG_Bad_T","desiredTemperature","7.5"))} else {return "-"} }
So wird die Temperatur zumindest bei valveposition > 50 gesetzt und bei < 50 durch einen - ersetzt. Leider wird es jetzt auch bei jedem Event die Temperatur gesetzt. Ich werde sehen, ob das zu Problemen führt...
Vermutlich ist das dein Problem gewesen. Ein userReading wird durch eine Änderung des selben Device getriggert. Also dein userReading auf dem MAX wird durch Event aus dem MAX getriggert und nicht aus dem DOIF
Bei userReadings kannst Du nach dem userReading Name ein Trigger (des selben Device natürlich) definieren
<reading>[:<trigger>] [<modifier>] { <perl code> }
Für mich war es aber das verwirrende, dass die Logik genau gegenteilig funktioniert hat. Also irgendwie hat ja doch was funktioniert.
Das war m.A. reiner Zufall. Z.B.:
- dein DOIF hat mit Bedingung 1 getriggert => wait 120
- inzwischen hat dein MAX wegen Temperatur die Kalkulation des userReadings getriggert; DOIF war aber noch nicht bei cmd_1
- Ende des waits, DOIF kommt auf cmd_1, aber das triggert keine Neukalkulation des userReadings