First execution of rule with script including 'wait' takes much longer than it should

Background: I have a tv ceiling mount that is controlled over tuya, which I have integrated via the smarthome/j tuya binding. Works fine, but for some reason the device requires an action to be quitted before another action is triggered. That means, when I send a command like “move_up” or “move_down”, I need to send the command “cancel” before I send the next command. This “cancel” is only doing something internally, it does not stop the movement of the ceiling.

To simplify the usage of the mount, I created a rule that sends the command “cancel”, whenever the according item is set to a state that is not “cancel”. To not send two commands to the device in a very short time, I have inserted an inline script as the first action which does nothing but just waiting for 400 ms.
Here is a screenshot of this quite simple rule:

Now the problem is that whenever openhab is restarted - or even only saving the rule again without doing any changes - the first execution of this rule does not take 400 ms like it should, but about 33 seconds, until the “cancel” command is send.
Here is a screenshot of the logs, where I triggered the rule twice after saving the rule. I separated the two executions in the logs with the red line:

As explained, the first execution takes in this case nearly 34 second, while the second execution (and every following one) only takes the expected 400 ms.

I’ve also tried the rule without the script. In that case it didn’t make any difference if it’s the first execution after saving the rule or the second execution, the command was sent immediately.
That’s why I’m thinking that the wait somehow induced the issue.

Could this be a bug? Or else, does someone have an idea, what the issue could be?
I’m thankful for any help!

This is a well known issue on 32-bit ARM processors (e.g. what an RPi runs on). The first time a JS Scripting rule is run after it gets loaded requires the Helper Library to be loaded. On 32-Bit ARM this appears to take 20-30 seconds.

There is evidence that running on an x86, amd64 processors or running 64-bit OS and Java even on ARM processors reduces this initial delay down by 10x (so 2-3 seconds).

If that isn’t an option for you, you will need to use something other than JS Scripting or Blockly for this specific rule. Note that for different reasons Rules DSL also will have a noticeable delay the first it’s run. In truth all the rule languages will be slightly delayed the first time it’s run. But jRuby’s delay at least will be pretty short. Nashorn JS is also very short as there’s no library to load at all.

tl;dr: it’s not the sleep, it’s the script engine

Hi @rlkoshak

Thanks a lot for the answer, that really should be the issue!
I’m running openhab on a RPi 4 with openhabian, so I do have a 64 bit processor.
But I checked again which version of the OS I installed back then and it seems I have chosen the 32 bit version of openhabian since I just went along with the recommendation in the docs: openHABian | openHAB

I guess I will have a look then at jRuby or Nashorn JS, especially for a simple wait it shouldn’t be very complex.

Thanks again and best regards
Özcan

There is a fine balance that needs to be reached. 64-bit OS/64-bit Java is going to require significantly more RAM than 32-bit and RAM is usually the limiting factor on SBCs. Since an RPi 3 is the minimum supported platform the best recommendation is probably still 32-bit. However, at least for now, the only solution to the delay problem is running on 64-bit. But even that brings the delay down to a couple seconds which is still too long for what you describe you need here.

I don’t know jRuby but their docs are very good.

Nashorn JS would be the following:

Java.type('java.lang.Thread').sleep(500);

The default installation of jruby will include the helper library, which will add several seconds to load time on an rpi.

To do a sleep, you don’t need the helper library, it’s simply:

sleep 0.4

To use jruby without loading the helper library, install the addon, and then set the require script to blank / spaces.

An alternative is to use a file-based rule. File-based rules are loaded / parsed when the file is modified, so on the first execution it’s already loaded.