executeCommandLine on a Windows machine

Can someone clarify my usage of executeCommandLine?
I am running openHab2 on a Windows 7 machine.
I am trying to use executeCommandLine in a very simple rule example.

The code below shows what I’m trying to do and the error messages I’m getting in the log file
(openhabinput.txt is a text file with a single line “the lights need adjustment” which I’ve tried placing in various folders)


//Turn on the wemo mini switch when openhab2 launches
rule "1st rule"

when
	System started
then
//	val input = "the lights need adjustment"//this works fine

//	val input = executeCommandLine ("echo the lights need adjustment")//doesn't work
		//[ERROR] [lipse.smarthome.io.net.exec.ExecUtil] - couldn't execute commandLine 'echo the lights need adjustment'
		//java.io.IOException: Cannot run program "echo": CreateProcess error=2, The system cannot find the file specified

//	val input = executeCommandLine("head -n 1 C:\\openhabinput.txt", 1000)//doesn't work
	val input = executeCommandLine("head -n 1 openhabinput.txt", 1000)//doesn't work, same error message
		//[WARN ] [lipse.smarthome.io.net.exec.ExecUtil] - Execution failed (Exit value: -559038737. 
		//Caused by java.io.IOException: Cannot run program "head" (in directory "."): CreateProcess error=2, The 
               //system cannot find the file specified)

	if (input.contains("lights")) Switch1_state.sendCommand(ON)
end

some of my many questions include:

  1. documentation of the Exec bindings does not seem to match the usage in this example:
    https://community.openhab.org/t/using-java-code-in-openhab2/38382/5
  2. all the other threads I could find on this forum seem to be using executeCommandLine on a UNIX system. What would be an example string for the executeCommandLine argument on Windows?
  3. in another thread, instead of “val input =” the programmer used “var string input =”. With a lowercase word “string”. I thought all object types in openHab2 are case sensitive. No?
    Thanks in advance
    Joe

Hello!

If I’m not mistaken, you should use @@ instead of blanks in executeCommandLine on Windows. So, the rule line should look like:

val input = executeCommandLine(“head@@-n@@1@@openhabinput.txt”, 1000)

Best regards,
Davor

No difference.

I’m not 100% certain, but I’m pretty sure Windows does not have echo or head commands.

If you bring up a cmd terminal and you commands won’t run there, it won’t run from executeCommandLine.

  1. That is because the Exec binding and executeCommandLine Action are two different things.

  2. From OH’s perspective it’s the same. But the command has to be a valid Windows command. I don’t know what/if there is an equivalent of echo or head on Windows.

  3. That was most likely a typo.

echo exists in windows. Not head.

echo does indeed exist in Windows cmd, but as you can see from my example code above it doesn’t work as the executeCommandLine argument:

In a Windows cmd console:

C:> Echo hello Joe
hello Joe

Has anyone here actually used executeCommandLine or the Exec bindings under Windows?

Because when you do an “echo” command from the windows command prompt, it’s executed by the running shell.

In my experience, when you want to call echo from a program you usually have to pass this to the OS:

cmd /c echo hi there

1 Like

Hello!

I’m using executeCommandLine on Windows, and it works without issues. Do you have path to “head.exe” in your System variables -> Path? Maybe you should try to call it with a full path instead:

val input = executeCommandLine(“C:\\head\\head@@-n@@1@@openhabinput.txt”, 1000)

for example (you should, of course, change C:\\head\\ to the actual path of head.exe executable).

Best regards,
Davor

Thanks for the help.
I’ve copied head.exe into the top level of my OS partition. And I’ve been trying some variations but I am still unable to read from or write to files.

Here is what my rule now looks like:

//Turn on the wemo mini switch when openhab2 launches
rule "1st rule"

when
	System started
then
	executeCommandLine ("cmd echo this is a test > openhaboutput.txt")//no error but no file appears
	val input = executeCommandLine("C:\\head@@-n@@1@@openhabinput.txt", 1000)//no errors reported but the if clause below doesn't fire
	if (input.contains("lights")) { 
		Switch1_state.sendCommand(ON)
	}
end

The rule loads and executes without reporting an error. However, even though The log file includes the report:
[INFO ] [lipse.smarthome.io.net.exec.ExecUtil] - executed commandLine 'cmd echo this is a test > openhaboutput.txt’
no file is written.
Also, the “if” clause is not satisfied (the switch does not turn on)

  1. can you see anything else that might be wrong?
  2. I am still trying to understand the debugging and tracing tools. In the meantime is there something quick I can do to examine the value of input? (Something similar to Java System.out.format or System.out.print)
  3. would I have a better chance of success by using the “output” channel of the Exec binding or is that the same as using the executeCommandLine action?
    Regards,
    Joe

I am using the exec binding under Windows, but I found that often it helps to just call a .bat file with the binding and then put the rest of commands in the .bat file. Maybe it is worth to give it a try?

1 Like

There really aren’t any.

https://docs.openhab.org/administration/logging.html#create-log-entries-in-rules

The Exec binding and executeCommandLine are completely separate. I don’t think there is a significant difference between the two approaches. Since you are using executeCommandLine now, stick with it. Don’t change at this point.

I’m still struggling. I’ve been trying many many variations on using executeCommandLine (batch files, DOS commands, Windows Shell, head etc.). No errors are being reported and the executeCommandLine command is being logged as having run. BUT I still am not able to either read from or write to files!
It would help me IMMENSELY if someone who is using executeCommandLine on a Windows platform could post a piece of their actual code, for example some rule they are using. I must be overlooking something.
Thanks in advance,
Joe
PS-if I can get this to work I think I am home free, for the time being, in having openhab do what I need it to do.

The excellent article on exec debugging suggests trying to log the output returned from the command:

val results = executeCommandLine("/bin/echo@@'The quick brown fox jumped over the lazy dog.'", 5000)
logInfo("execTest", results)

I’m still trying (unsuccessfully) to read from a file.
I’m trying to debug the executeCommandLine action using the documentation here:
https://community.openhab.org/t/how-to-solve-exec-binding-problems/18131
in the following rule, the switch does not turn on.


//Turn on the wemo mini switch when openhab2 launches
rule "first rule"

when
	System started
then
//	val input = "the lights need adjustment"//this works fine
	val input = executeCommandLine("C:\\head@@-n@@1@@openhabinput.txt", 5000)//no errors, but the switch does not turn on
	logDebug("testExec", input)

	if (input.contains("lights")) {
		Switch1_state.sendCommand(ON)
	}
end

Also, I don’t see any debugging information!
Am I understanding the documentation correctly? I uninstalled the Exec bindings.
I wasn’t sure what to put for the 1st argument of logDebug. In addition to “testExec” I tried the name of the rule and the name of the .rules file. Didn’t make any difference.
I also used the console “log” command to change the log level to DEBUG. This produced a very large amount of output into the log file but there was no reporting of the value of “input”.
Regards,
Joe

Where is the txt file? You may need to use the full path for it as well. I’m not sure what directory this runs from.

You should review the logging section of the docs.

It shows the name of the package to set for logging (org.eclipse.smarthome.model.script), along with examples.

I am still trying unsuccessfully to get executeCommandLine to work.
I have started a new topic to get help in debug logging within rules:
https://community.openhab.org/t/debug-logging-in-rules/38764
In the meantime, I have found a (pretty crude) workaround that enables me to control the openhab application from other programs, possibly running on another computer:
For each operation I want openhab2 to perform, I have a rule file which I keep in a directory outside of the rules folder. For example, the following rule file named “switch1_state_on.rules”

//Turn on the wemo mini switch when openhab2 launches
//or when this file is modified or loaded
rule "switch1_state_on"

when
	System started
then

	Switch1_state.sendCommand(ON)
end

The other application simply runs a batch file that copies this rule file into the openhab rules folder where it immediately triggers.

Hello!

Since you need these files to interact with OH from external applications, have you considered using REST API? If the interaction consists of item’s postUpdate and sendCommand, this would be the easiest way to achieve this.

Best regards,
Davor

1 Like

Thanks for the suggestion. I will look into that.
Regards,
Joe

Hi Joseph !

I am also running OpenHAB2 on a Windows 7 machine (ZOTAC Nano CI320) and I have many rules with executeCommandLine without any problem.

I tried to reproduce your use case :

rule "Un test"
when
    System started
then
    val input = executeCommandLine("C:\\OH_utils\\head@@-n@@1@@C:\\OH_utils\\essai.txt", 1000)
    logInfo("DEBUG", "From essai.txt : " + input)
    if (input.contains("first")) logInfo("DEBUG", "the line contains <first> !")
end

It works fine with this output in openhab.log :

2018-01-16 10:56:29.784 [INFO ] [eclipse.smarthome.model.script.DEBUG] - From essai.txt : This is the first line of my file...
2018-01-16 10:56:29.792 [INFO ] [eclipse.smarthome.model.script.DEBUG] - the line contains <first> !

I don’t understand why it does not work for you. Just one point : essai.txt is in the same directory as head.exe, but if I don’t use the full path of essai.txt, I get an error.

To be sure of your setup, have you tried a very simple rule as :

executeCommandLine("notepad.exe")

Best regards.

1 Like