I suggest you do something I’ve done in most of my DP tutorials. Break it down into simpler parts with an example or examples that are just complex enough to illustrate the concept. Often these examples are not all the practical but they are easy to understand and illustrate the overall approach without a lot of extra details getting in the way.
Then provide a comprehensive example showing an application of the DP to a real world problem. In the comprehensive example use comments to point out those lines/rules/etc that implement the DP.
Ultimately the DP is trying to show a way to issue a command, wait for an event, then issue some more commands. So maybe come up with a toy example that illustrates the concept really well, then show your full implementation without trying to dumb it down to show it in use in a real world situation.
NOTE: I can think of some very elegant ways to implement this in Scripted Automation that might make it worth pursuing. For example, using Item Metatada you can define metadata that defines which Items to wait until they reach which states before commanding another Item.
Switch firstCommand { waitfor="status"[{command=ON, states={ Foo=OFF, Bar=ON }, secondCommand=ON}, {command=OFF, states={Foo=ON,Bar=OFF}, thirdCommand=OFF}] }
I’m totally guessing at some of the syntax above but it’s something like that. The above would tell the Rule that on an ON command to wait for Foo to turn OFF and Bar to turn ON and when that occurs sendCommand ON to secondCommand. When firstCommand receives OFF as a command wait for Foo to turn ON and Bar to turn OFF and issue an OFF command to thirdCommand Item.
The Python Rule would look through all the Items with the waitfor metadata and it can dynamically generate triggers for a Rule to trigger when it )in this case firstCommand
receives a command. This Rule will dynamically create two Rules to trigger when Foo receives the right command and Bar receives the right command and a counter that counts up as the Rules get triggered. When the count gets to the number of states being waited on trigger the command to the new Item.
With an approach like that you don’t have to include implementation specifics in the part of the Rule that handles the waiting for the states. And you can string it all together using Item metadata.
I don’t have time to look up all the right syntax right now but I think JSR223 Jython Replacement for Expire Binding has everything from a syntax perspective that’s needed for examples.
Another approach, and perhaps a simpler approach could be accomplished with a simple while loop. Scripted Automation doesn’t have the same limitations as Rules DSL so having long running Rules isn’t so big of a deal. A simple “waitForState” module could be used that loops until the passed in Item reaches the passed in state (returns immediately if it is already in that state, returns with an error if it exceeds the passed in timeout).
Then you don’t need quite so much redirection. One Item receives a command that triggers a Rule. The Rule sends some commands, waits for Items to reach the right state, then continues on running. This would probably be the simplest approach of them all I suspect. I could see this being pretty useful overall. It would make implementing state machines a little easier in some cases.
I’ve already implemented something like this in JavaScript for the work I’ve done on HestiaPi.
context.waitForUpdateState = function(item, state, maxSecs) {
var count = 0;
while(count < maxSecs && (items[item] != state)){
count++;
java.lang.Thread.sleep(1000);
}
};
This would be the worst thing imaginable in Rules DSL but it is a pretty elegant solution in Scripted Automation. Were I to make it more generic I’d probably sleep in 100 msec increments but the concept would remain the same.