Java Switch Case in openhab rules

I am trying to create a rule which is run when 1 of 2 relays is changed. To clearify more:
1 relay is a transformer which is converting power for solenoid 1 and 2. PumpRelay01 and 02 are the solenoid relays. The pumps can therefore only be run with pumprelay01 + transformer, pumprelay02 + transformer, pumprelay01 + pumprelay02 + transformer, you get the idea.

I have some experience in Java so I was tinking of using a Java switch in my code, however I do not seem to get it to work and searching on either case or switch does not give me any answer if it is working.
Would someone be so nice to help me out (wheter this is going to work and if the switch is supported):smile:

import org.joda.time.*
import org.openhab.core.library.types.*
import org.openhab.core.persistence.*
import org.openhab.model.script.actions.*

rule "Switch transformer ON/OFF"
when
    Item Pump01 changed or
    Item Pump02 changed or
    Item Relay02 changed
then
    switch {
            case Pump01.state==ON AND Pump02.state==ON AND Relay02.state==ON:
            	// Do nothing, switches correct
            	break;
		case Pump01.state==ON AND Pump02.state==ON AND Relay02.state==OFF:
			// Turn Relay02 ON
			sendCommand(Relay02, ON);
            	break;
		case Pump01.state==OFF AND Pump02.state==ON AND Relay02.state==ON:
			// Do nothing, switches correct
            	break;
		case Pump01.state==OFF AND Pump02.state==ON AND Relay02.state==OFF:
			// Turn Relay02 ON
			sendCommand(Relay02, ON);
            	break;
		case Pump01.state==ON AND Pump02.state==OFF AND Relay02.state==ON:
			// Do nothing, switches correct
            	break;
		case Pump01.state==ON AND Pump02.state==OFF AND Relay02.state==OFF:
			// Turn Relay02 ON
			sendCommand(Relay02, ON);
            	break;
		case Pump01.state==OFF AND Pump02.state==OFF AND Relay02.state==OFF:
			// Do nothing, switches correct
            	break;
		case Pump01.state==OFF AND Pump02.state==OFF AND Relay02.state==ON:
            	// Turn Relay02 OFF
			sendCommand(Relay02, OFF);
            	break;
            default: break;
        }
end

I’m not quite sure but I think your switch statement is missing a main expression to switch on:

switch myString {
  case myString.length > 5 : "a long string."
  case 'some'              : "It's some string."
  default                  : "It's another short string."
}

See the Xtend syntax documentation here: https://eclipse.org/xtend/documentation/203_xtend_expressions.html

You are right, switch in java is only able to handle 1 variable and not the 3 like I wanted.
What is possible to do I think is to merge the 3 variables to 3bit length value: 010 (pump1 off, pump2 on, transformer off).

Then I can just match all cases like:
case ‘010’: “do something or not”

Will try later today.

An important thing to realize is that even though Java classes are available in the rules, the Rules and Scripts are written in the Xtend language, not Java. Switch statements in Xtend work significantly differently than they do in Java.

Review the page linked to by @thorsten_gilfert.

Also, I think the symbol for AND should actually be &&.

That being said, something like this might work:

switch Pump01 {
    case Pump01.state==ON && Pump02.state==ON && Relay02.state==OFF: sendCommand(Relay02, ON)
    case Pump01.state==OFF && Pump02.state==ON && Relay02.state==OFF: sendCommand(Relay02, ON)
    case Pump01.state==ON && Pump02.state==OFF && Relay02.state==OFF: sendCommand(Relay02, ON)
    case Pump01.state==OFF && Pump02.state==OFF && RElay02.state==OFF: sendCommand(Relay02, OFF) 
}

There is no need to have cases that do nothing in the statement. I’m not sure if Xtend will even let you do that actually. One big thing to note about Xtend switch statements is that they do not fall through so there is no need for the breaks.

That being said, I think you can collapse this into a single if/else statement:

if(Relay02.state == OFF && (Pump01.state==ON || Pump02.state==ON)) sendCommand(Relay02, ON)
else if(Relay02.state == ON && Pump01.state == OFF && Pump02.state==ON) sendCommand(Relay02, OFF)

Rich

1 Like

Based on the above input I adjusted the code and now it is working as should:

import org.openhab.core.library.types.*
import org.openhab.core.persistence.*
import org.openhab.model.script.actions.*

rule "Switch transformer ON/OFF"
when
    Item Pump01 changed or
    Item Pump02 changed or
    Item Relay02 changed
then
// 	println("Test")
	var String TestString
	TestString = ""
	
	if (Pump01.state==ON){
   		TestString = TestString+"1"
	}
   	else{
   		TestString = TestString+"0"
   	}

   	if (Pump02.state==ON){
   		TestString = TestString+"1"
   	}
   	else{
   		TestString = TestString+"0"
   	}
   	
   	if (Relay02.state==ON){
   		TestString = TestString+"1"
   	}
   	else{
   		TestString = TestString+"0"
   	}
  // println("Test")
    switch TestString {
            //case "111":	// Do nothing, switches correct
			case "110":	// Turn Relay02 ON
				sendCommand(Relay02, ON)
			//case "011": // Do nothing, switches correct
			case "010": // Turn Relay02 ON
				sendCommand(Relay02, ON)
			//case "101": // Do nothing, switches correct
			case "100": // Turn Relay02 ON
				sendCommand(Relay02, ON)
			//case "000": // Do nothing, switches correct
			case "001": // Turn Relay02 OFF
				sendCommand(Relay02, OFF)
        }
    Thread::sleep(1000)
end

There might be better and optimized ways to do it, but for now I am quite happy with the result.