[PRERELEASE] Virtual Prestaging

Prestaging is a handy capability -- you can set the level for a light to use before it's turned on. Unfortunately, level prestaging is not a feature of Zigbee and there is not currently a path toward native support in Hubitat drivers. The situation is even bleaker for CT and RGB capabilities.

The generally recommended solution is a RM rule for each target device to apply the desired configuration when it turns on, but if you have many devices, this is both tedious to configure and troublesome to update. This app attempts to patch that hole. Select a primary (likely virtual) device that has the desired values, along with a set of secondary devices you want to follow it. When the primary device changes, all the secondary devices which are on will be updated to follow it. When a secondary device turns on, the selected properties from the primary device will be sent to it immediately.

If the target device supports the LevelPreset capability, levels will be preset to it immediately, regardless of switch state. If better prestaging capabilities are defined, the app will be updated to use them.

You can install the app from here and here; also available on HPM.

(I discovered only after writing the app that the concept is very similar to Virtual Smarter Bulb. There are some different design choices, but the overall effect will be much the same. Feel free to use whichever suits.)


Not intending to take attention away from this release or minimize its potential utility for those who may want to try it.

But I think that the lack of built-in prestaging is actually deliberate at this point, and not going to expand in the future. See recent quote below from another thread:

1 Like

I would welcome staff input, but I believe that's talking about the unpredictable device option which silently changes the behavior of setLevel(). When that option is used, apps can't predict what behavior to expect when they call setLevel(). It was added to some drivers, and is now being backed out as a bad direction.

Instead, they added the separate LevelPreset capability which adds a different method, and both methods have clear expectations about their behavior. Apps can query devices and know what to expect.

This app will use the new capability if it's present; if it's not, then it does the best it can (flash bright, as mentioned in the thread you linked).


Makes sense, thanks.

In other older discussions, there was mention of a need for new driver capabilities, I believe in order for apps to know whether a driver supports certain prestaging functions. But I’m not a dev so much of this is my best guess at what it all means :upside_down_face:.

Regardless, thanks for sharing your work with the community :slightly_smiling_face:.


Hm, I may stand corrected -- in this post, @bravenel says the capability was added in error and needed to be removed from the capability list (which still hasn't happened).

Regardless, this app is able to replace having a separate RM rule for each device, so I think it has a place regardless of the future of in-driver prestaging.

The generic problem is that apps cannot tell if pre-staging is available or not for any given device. So there is no way to know to offer it or not, and if offered, how it should work.

But wasn't that what the LevelPreset capability was for? Or is the issue that drivers can't dynamically expose capabilities, so a generic driver with the capability would be a bad fit for a device without it?

Well, in theory. But, with only a small subset of devices implementing it, it still doesn't make sense.

When we first added the capability, we mistakenly thought that certain Zigbee bulbs supported it. That turned out to be wrong, and that Zigbee does not support it at all.


Do you think I could pair this app with circadian daylight to get around my lights coming on at their last color then changing?

That's actually very close I wrote it for. :wink: It doesn't totally eliminate the flash, but the time to switch is a lot faster than waiting for CD's next update cycle. The color change is sent a few hundred milliseconds after the light reports turning on; it might look like part of turning on depending on the bulb. On mine, if you're watching, you can see a moment of the old value followed immediately by a transition to the new one.

Have CD set the color temperature on a virtual device, then use this to push it to the other devices.

@mbishop I'm a big fan of virtual prestaging. Yesterday, I moved from an old version to HPM and now my disable switches are not working. In checking the logs, it looks like an error is being generated that causes the app to not follow the disable switches when turned on. I'm getting the following:

org.codehaus.groovy.runtime.metaclass.MissingMethodExceptionNoStack: No signature of method: java.lang.String.call() is applicable for argument types: (com.hubitat.hub.domain.Event) values: [com.hubitat.hub.domain.Event@7978c3]
Possible solutions: wait(), chars(), any(), wait(long), each(groovy.lang.Closure), any(groovy.lang.Closure) (initialize)

Basically, my disable switch went on at 7:42:26.637am, this error logged at 7:42:26.729am, and the light reverted back to the virtual bulb setting at 7:42:37.577am even though my disable switch was still on. I'm going to remove the HPM instance and try just pasting the raw code to see if works, but wanted to give you a head's up.

Thanks -- I'll double-check the code later this morning.

As a quick follow up, the same error is also present when I just paste the raw code instead of using HPM.

Sorry I didn't get to this as quickly as I'd hoped. I just pushed an update to HPM that should address this, and behave a little better around the disable switch to boot.

In basic testing, it looks like things are working again. I appreciate it and will keep an eye if anything comes up. I utilize this app for the vast majority of my lighting, so I’m a big fan!

1 Like

@mbishop A quick update, but it appears that there is a similar error still being generated. It doesn't seem to affect the switch, but it is present. I'm seeing the following in the logs:

app:2702023-07-10 07:30:00.568 AMerrororg.codehaus.groovy.runtime.metaclass.MissingMethodExceptionNoStack: No signature of method: user_app_evequefou_Virtual_Prestaging_Child_167.switchChanged() is applicable for argument types: (com.hubitat.hub.domain.Event) values: [com.hubitat.hub.domain.Event@12410bd] (switchChanged)
app:2702023-07-10 07:30:00.338 AMdebugSwitch changed to off (enabled)
app:2702023-07-10 06:00:00.498 AMerrororg.codehaus.groovy.runtime.metaclass.MissingMethodExceptionNoStack: No signature of method: user_app_evequefou_Virtual_Prestaging_Child_167.switchChanged() is applicable for argument types: (com.hubitat.hub.domain.Event) values: [com.hubitat.hub.domain.Event@1c19fb4] (switchChanged)
app:2702023-07-10 06:00:00.474 AMdebugPrimary device changed: colorTemperature to 2657
app:2702023-07-10 06:00:00.453 AMdebugSwitch changed to on (disabled)

It doesn't seem to affect the operation; though, I did have a weird issue with lights turning off and then on again with the virtual bulb settings being applied. It might be a timing issue and unrelated to the app's operation.

Can you try opening the app and clicking Done? If that doesn't do it, look at the app properties and check what handlers are registered for the switch.

I hit done for each of my five child devices and the main one. This seems to have cleared up the error with the turning on the disable switch. However, it still kicks an error when I turn off the disable switch.

As for the handlers, you’ll need to guide me on how to do that.

Finally, I went back and tried different versions of the child app from your GitHub. I had to go back to your February revision in order for the error to now show up in the logs. The good news is that disable switch still works in your update from Friday.

I found the missing line from the change; the latest HPM update ought to clear it up.

Thank you for the update! I can confirm that there is no more error messages in my log.

1 Like