modbus Bitweise schreiben Esera Station 200

Einrichtung der openHAB Umgebung und allgemeine Konfigurationsthemen.

Moderatoren: seppy, udo1toni

Antworten
exceptio
Beiträge: 15
Registriert: 16. Mär 2019 07:30

modbus Bitweise schreiben Esera Station 200

Beitrag von exceptio »

Hallo Leute,

ich benötige mal bitte eure Hilfe. Ich komme nicht mehr weiter. Ich möchte bei meiner Esera Homestation Bitweise schreiben. Kann mir da jemand helfen?

Esera Station 200

https://www.esera.de/produkte/1-wire-sm ... t-home-iot

das aktuelle openhab2 mit einem raspberrypi 3

In meinem Beispiel OWD2 ist es ein 8 Fach Schaltmodul

modebus.think

Code: Alles auswählen

Bridge modbus:serial:esera [port="/dev/ttyUSB0",baud=19200,id=1,dataBits=8,parity="none",stopBits="1.0",encoding="rtu"] {

	 Bridge poller owd1 [ start=40100, length=16, refresh=5000, type="holding"] {
		Thing data owd1temp [ readStart="40100", readValueType="uint16", readTransform="teilen100.js"]
	}

	 Bridge poller owd2 [ start=40200, length=16, refresh=1000, type="holding"] {
		Thing data owd2ch1 [ readStart="40204.0", readValueType="bit" ]
		Thing data owd2ch2 [ readStart="40204.1", readValueType="bit" ]
		Thing data owd2ch3 [ readStart="40204.2", readValueType="bit" ]
		Thing data owd2ch4 [ readStart="40204.3", readValueType="bit" ]
		Thing data owd2ch5 [ readStart="40204.4", readValueType="bit" ]
		Thing data owd2ch6 [ readStart="40204.5", readValueType="bit" ]
       	        Thing data owd2ch7 [ readStart="40204.6", readValueType="bit" ]
		Thing data owd2ch8 [ readStart="40204.7", readValueType="bit" ]
	}
}
Bitweise lesen funktioniert. Mit dem schreiben habe ich meine massiven Probleme. Und leider zu wenig Ahnung. Kann mir jemand helfen, vielleicht mit einem Beispiel oder ähnlichen.

Bild

Grüße
Sebastian
Du hast keine ausreichende Berechtigung, um die Dateianhänge dieses Beitrags anzusehen.

AnderOstsee
Beiträge: 24
Registriert: 15. Jul 2019 17:08

Re: modbus Bitweise schreiben Esera Station 200

Beitrag von AnderOstsee »

Hallo Sebastian,

genau damit habe ich mich noch nicht beschäftigen können, aber vielleicht hilft dieser Link etwas weiter:
https://community.openhab.org/t/bitwise ... ster/77123

grüße

ralf

exceptio
Beiträge: 15
Registriert: 16. Mär 2019 07:30

Re: modbus Bitweise schreiben Esera Station 200

Beitrag von exceptio »

Hallo Ralf,

ich bin mir nicht ganz sicher ob ich es richtig umgesetzt habe.

.things (mein ReadTransform geht auch nicht)

Code: Alles auswählen

[WARN ] [ernal.handler.ModbusDataThingHandler] - Channel number will not be updated since transformation was unsuccessful. Channel is expecting the following data types [DecimalType, QuantityType, UnDefType]. Input data: number value 1912 (value type 'uint16' taken into account) and bool value true. Transformation: Transformation@8ed10d[tranformation=teilen100.js,transformationServiceName=<null>,transformationServiceParam=<null>]

Code: Alles auswählen

Bridge modbus:serial:esera [port="/dev/ttyUSB0",baud=19200,id=1,dataBits=8,parity="none",stopBits="1.0",encoding="rtu"] {

	 Bridge poller owd1 [ start=40100, length=16, refresh=5000, type="holding"] {
		Thing data owd1temp [ readStart="40100", readValueType="uint16"] //, readTransform="teilen100.js"
	}

	 Bridge poller owd2 [ start=40200, length=16, refresh=1000, type="holding"] {
		Thing data owd2ch0 [ readStart="40204", readValueType="uint16", writeStart="40202", writeValueType="uint16", writeType="holding" ]
		Thing data owd2ch1 [ readStart="40204.0", readValueType="bit" ]
		Thing data owd2ch2 [ readStart="40204.1", readValueType="bit" ]
		Thing data owd2ch3 [ readStart="40204.2", readValueType="bit" ]
		Thing data owd2ch4 [ readStart="40204.3", readValueType="bit" ]
		Thing data owd2ch5 [ readStart="40204.4", readValueType="bit" ]
		Thing data owd2ch6 [ readStart="40204.5", readValueType="bit" ]
                Thing data owd2ch7 [ readStart="40204.6", readValueType="bit" ]
		Thing data owd2ch8 [ readStart="40204.7", readValueType="bit" ]
	}
}
.items (nur ein Teil)

Code: Alles auswählen

Number Reg_Image  "OWD2 [%d]" { channel="modbus:data:esera:owd2:owd2ch0:number", autoupdate="false" }
Switch   Bedroom_Light            "Licht Schlafzimer"  <light>              (Bedroom, gLight)            ["Lighting", "Switchable"]         {channel="modbus:data:esera:owd2:owd2ch1:switch", autoupdate="false"}
Switch   Bathroom_Light           "Licht Badezimmer"   <light>              (Bathroom, gLight)           ["Lighting", "Switchable"]         {channel="modbus:data:esera:owd2:owd2ch2:switch", autoupdate="false"}
Switch   Kitchen_Light_1          "Licht Küche 1"      <light>              (Kitchen, gLight)            ["Lighting", "Switchable"]         {channel="modbus:data:esera:owd2:owd2ch3:switch", autoupdate="false"}

.rules

Code: Alles auswählen

import java.math.BigInteger // we need this for testBit

rule "update hvac register"
when
    Member of Owd2 received command
then
   var register = BigInteger.valueOf(0)  // we need BigInteger type to use testBit
   if ( Reg_Image.state != NULL && Reg_Image.state != UNDEF) { // avoid using invalid register image
       register = (Reg_Image.state as DecimalType).toBigDecimal.toBigInteger // use existing image
   }
   switch triggeringItem.name {    // act on switched Item name to change only one bit
      case "Bedroom_Light" : {
         if  (receivedCommand == ON) {
            register = register.setBit(0)
         } else if (receivedCommand == OFF) { // by testing both, we will ignore REFRESH commands
            register = register.clearBit(0)
         }
      }
      case "Bathroom_Light" : {
         if  (receivedCommand == ON) {
            register = register.setBit(1)
         } else if (receivedCommand == OFF) {
            register = register.clearBit(1)
         }
      }
      case "Kitchen_Light_1" : {
         if  (receivedCommand == ON) {
            register = register.setBit(2)
         } else if (receivedCommand == OFF) {
            register = register.clearBit(2)
         }
      }
   }
    // at last, write to Modbus
    Reg_Image.sendCommand(register)
end
.log

Code: Alles auswählen

2019-10-11 10:01:53.087 [WARN ] [ernal.handler.ModbusDataThingHandler] - Thing modbus:data:esera:owd2:owd2ch2 'Modbus data': not processing command OFF since writeStart is missing and transformation output is not a JSON

==> /var/log/openhab2/events.log <==

2019-10-11 10:01:54.289 [ome.event.ItemCommandEvent] - Item 'Kitchen_Light_1' received command OFF

==> /var/log/openhab2/openhab.log <==

2019-10-11 10:01:54.297 [WARN ] [ernal.handler.ModbusDataThingHandler] - Thing modbus:data:esera:owd2:owd2ch3 'Modbus data': not processing command OFF since writeStart is missing and transformation output is not a JSON

==> /var/log/openhab2/events.log <==

2019-10-11 10:01:55.341 [ome.event.ItemCommandEvent] - Item 'Bedroom_Light' received command OFF

==> /var/log/openhab2/openhab.log <==

2019-10-11 10:01:55.349 [WARN ] [ernal.handler.ModbusDataThingHandler] - Thing modbus:data:esera:owd2:owd2ch1 'Modbus data': not processing command OFF since writeStart is missing and transformation output is not a JSON

Wenn ich bei Modbus data OWD2 einen Wert zwischen 0 und 255 gebe, schreibe ich auch und die release machen das was sie sollen.

1.PNG

Würde mich freuen wenn mir weiter geholfen werden könnte

Grüße
Sebastian
Du hast keine ausreichende Berechtigung, um die Dateianhänge dieses Beitrags anzusehen.

exceptio
Beiträge: 15
Registriert: 16. Mär 2019 07:30

Re: modbus Bitweise schreiben Esera Station 200

Beitrag von exceptio »

Hallo,

ich möchte die gefundene Lösung nicht vorenthalten. Hatte Hilfe. Funktioniert soweit.

.rule

Code: Alles auswählen

import java.math.BigInteger // we need this for testBit

// rule immer unique 
rule "update OWD2 register ON"
when
   Member of gLight received command ON
then
   if ( triggeringItem.state != NULL && triggeringItem.state != UNDEF) { // avoid using invalid register image
      var register = (Reg_Image.state as DecimalType).toBigDecimal.toBigInteger // use existing image
      // logWarn("myLog", "update for " + triggeringItem.name)
      // logWarn("myLog", "update for " + triggeringItem)

      switch triggeringItem.name {    // act on switched Item name to change only one bit
         case "Bedroom_Light" : {
            register = register.setBit(0)
         }
         case "Bathroom_Light" : {
            register = register.setBit(1)
         }
         case "Kitchen_Light_1" : {
            register = register.setBit(2)
         }
         case "Kitchen_Light_2" : {
            register = register.setBit(3)
         }
         case "LivingRoom_Light_1" : {
            register = register.setBit(4)
         }
         case "LivingRoom_Light_2" : {
            register = register.setBit(5)
         }
         case "LivingRoom_Light_3" : {
            register = register.setBit(6)
         }
         case "Stairwell_Light" : {
            register = register.setBit(7)
         }      
      }

      // at last, write to Modbus
      Reg_Image.sendCommand(register)
   }
end

// rule immer unique 
rule "update OWD2 register OFF"
when
   Member of gLight received command OFF
then
   if ( triggeringItem.state != NULL && triggeringItem.state != UNDEF) { // avoid using invalid register image
      var register = (Reg_Image.state as DecimalType).toBigDecimal.toBigInteger // use existing image
      // logWarn("myLog", "update for " + triggeringItem.name)
      // logWarn("myLog", "update for " + triggeringItem)

      switch triggeringItem.name {    // act on switched Item name to change only one bit
         case "Bedroom_Light" : {
            register = register.clearBit(0)
         }
         case "Bathroom_Light" : {
            register = register.clearBit(1)
         }
         case "Kitchen_Light_1" : {
            register = register.clearBit(2)
         }
         case "Kitchen_Light_2" : {
            register = register.clearBit(3)
         }
         case "LivingRoom_Light_1" : {
            register = register.clearBit(4)
         }
         case "LivingRoom_Light_2" : {
            register = register.clearBit(5)
         }
         case "LivingRoom_Light_3" : {
            register = register.clearBit(6)
         }
         case "Stairwell_Light" : {
            register = register.clearBit(7)
         }      
      }
      
      // at last, write to Modbus
      Reg_Image.sendCommand(register)
   }
end
Muss für seinen eigenen Einsatz natürlich noch angepasst werden.

Grüße Sebastian

Benutzeravatar
udo1toni
Beiträge: 13864
Registriert: 11. Apr 2018 18:05
Answers: 222
Wohnort: Darmstadt

Re: modbus Bitweise schreiben Esera Station 200

Beitrag von udo1toni »

Tipp: Man kann beide Rules zu einer Rule zusammenfassen.

Code: Alles auswählen

import java.math.BigInteger // we need this for testBit

// rule immer unique 
rule "update OWD2 register"
when
    Member of gLight received command
then
    var register = (Reg_Image.state as DecimalType).toBigDecimal.toBigInteger // use existing image
    logInfo("OWD2update","update for {}",triggeringItem.name)
    var Number nReg = -1
    switch triggeringItem.name {    // act on switched Item name to change only one bit
        case "Bedroom_Light"      : nReg=0
        case "Bathroom_Light"     : nReg=1
        case "Kitchen_Light_1"    : nReg=2
        case "Kitchen_Light_2"    : nReg=3
        case "LivingRoom_Light_1" : nReg=4
        case "LivingRoom_Light_2" : nReg=5
        case "LivingRoom_Light_3" : nReg=6
        case "Stairwell_Light"    : nReg=7
    }
    if(nReg > -1) {
        register = (if(receivedCommand == ON) register.setBit(nReg) else register.clearBit(nReg)
        // at last, write to Modbus
        Reg_Image.sendCommand(register)
    } else
        logWarn("OWD2update","Something went wrong! Can't find Bit for {}!",triggeringItem.name)
end
Beim Import bin ich mir ziemlich sicher, dass der in OH2 nicht mehr gebraucht wird, aber sicherheitshalber...

Die Prüfung des Status des triggernden Items ist hingegen Unsinn, denn dieser Status spielt ja nun zu keinem Zeitpunkt eine Rolle.
Das Kommando kann (mal vorausgesetzt, alle Member der Gruppe gLight sind vom Typ Switch) nur ON oder OFF heißen, es gibt kein anderes Kommando. Womit hier hervorragend der ternäre Operator eingesetzt werden kann.
Die Wertzuweisung nach register ist abhängig vom receivedCommand, welches Bit beeinflusst wird, wird vorher durch switch festgelegt. Sollte aus irgendeinem Grund switch keinen Wert setzen, wird auch nichts nach Reg_Image geschrieben.

Weiterhin habe ich die logWarn Zeile oben gegen logInfo getauscht (man könnte sogar darüber nachdenken, hier auf logDebug zu gehen) und lasse unten nur bei Fehlschlag ein logWarn ausgeben.

Ich hab gerade heute davon gelesen, dass jemand logWarn einsetzt, weil die Zeilen im Log farblich hervorgehoben werden. Das ist, mit Verlaub, am System vorbei.
Man kann das LogLevel (für jeden Logger einzeln, weshalb es sinnvoll ist, jeder Rule einen eigenen Logger zu spendieren) zur Laufzeit von openHAB festlegen, sprich, man muss keine log-Anweisungen auskommentieren, um sie zu unterdrücken. Ebenfalls kann man sowohl in frontail (Das Log im Browser) als auch auf der Kommandozeile komfortabel die Ausgaben des Logs filtern, wenn man Angst hat, die entscheidenden Zeilen zu verpassen.
Die verschiedenen log Level sind ausschließlich dazu da, verschieden wichtige Meldungen zu erzeugen, nebensächlich (DEBUG), informativ (INFO), wichtig (WARN), extrem wichtig (ERROR). Wenn man nur wichtige Meldungen sehen möchte, ändert man das log Level auf WARN und bekommt in der Folge weder INFO noch DEBUG zu sehen. Man kann das log sogar komplett stumm schalten, was verschiedentlich für Erweiterungen schon notwendig war, da z.B. für konfigurierte, aber abgeschaltete Geräte ständig ERROR-Meldungen kamen (bis ein Entwickler den korrekten logLevel dafür eingebaut hat - Debug)
openHAB4.1.2 stable in einem Debian-Container (bookworm) (Proxmox 8.1.5, LXC), mit openHABian eingerichtet

exceptio
Beiträge: 15
Registriert: 16. Mär 2019 07:30

Re: modbus Bitweise schreiben Esera Station 200

Beitrag von exceptio »

Hallo Udo,

hatte wenig Zeit zum testen, deine Rule funktioniert leider nicht, er schreibt nicht in das "Reg_Image.sendCommand(register)". Wenn jemand noch einen Moment Zeit investieren würde. Das soll mein Basis Baustein werden. Wenn etwas log benötigt wird poste ich ihn gerne um es zu unterstützen.

Grüße

Sebastian

Benutzeravatar
udo1toni
Beiträge: 13864
Registriert: 11. Apr 2018 18:05
Answers: 222
Wohnort: Darmstadt

Re: modbus Bitweise schreiben Esera Station 200

Beitrag von udo1toni »

Jepp, es fehlt eine Klammer. Bzw. es ist eine zu viel (je nachdem, wie man es betrachtet) Die fragliche Zeile:

Code: Alles auswählen

register = (if(receivedCommand == ON) register.setBit(nReg) else register.clearBit(nReg)
entweder

Code: Alles auswählen

register = (if(receivedCommand == ON) register.setBit(nReg) else register.clearBit(nReg))
oder

Code: Alles auswählen

register = if(receivedCommand == ON) register.setBit(nReg) else register.clearBit(nReg)
dann sollte es klappen (es sei denn, ich hab noch mehr übersehen...)
openHAB4.1.2 stable in einem Debian-Container (bookworm) (Proxmox 8.1.5, LXC), mit openHABian eingerichtet

exceptio
Beiträge: 15
Registriert: 16. Mär 2019 07:30

Re: modbus Bitweise schreiben Esera Station 200

Beitrag von exceptio »

Hallo Udo,

dankeschön funktioniert.

Grüße
Sebastian

Antworten