autoupdate = false was created to handle the case where you have a device that automatically report’s its state changes to OH. Imagine the following scenario.
- user clicks on sitemap to send ON command to an Item
- Item forwards the ON command to the binding
- If
autoupdate=true
, the Item changes state to ON. Ifautoupdate=false
the Item remains OFF. - There was an error and the device never turned OFF.
If you are using autoupdate=true
(which is the default) then the Item will be set to ON and everything will assume that the device is ON. If you use autoupdate=false, the Item will remain OFF because we never received an update telling us that it actually turned OFF.
So it was created to give OH the ability to more closely represent the state of devices in the unfortunately rare case where the devices positively report back they state to OH when they change state.
Probably not. I think what you are looking for is Design Pattern: Manual Trigger Detection. What you need it a way to distinguish between an incoming update that was caused by your Rule versus one caused by flipping the switch some other way.
I do something similar with my lighting. When it is cloudy the light turns on during the day. However, is someone manually turns on/off the light during that time of day then the light will stay in that state and no long turn on or off as the cloud conditions change.
// Theory of operation: any change in the relevant lights that occur more than five seconds after
// the change to DAY or after a change caused by cloudy is an override
rule "Watch for overrides"
when
Member of gLights_ON_DAY changed
then
// wait a minute before reacting after vTimeOfDay changes, ignore all other times of day
if(vTimeOfDay.state != "DAY" || vTimeOfDay.lastUpdate("mapdb").isAfter(now.minusMinutes(1).millis)) return;
// Assume any change to a light that occurs more than n seconds after time of day or cloudy is a manual override
val n = 5
val causedByClouds = vIsCloudy.lastUpdate("mapdb").isAfter(now.minusSeconds(n).millis)
val causedByTime = vTimeOfDay.lastUpdate("mapdb").isAfter(now.minusSeconds(n).millis)
if(!causedByClouds && !causedByTime) {
logInfo(logName, "Manual light trigger detected, overriding cloudy control for " + triggeringItem.name)
postUpdate(triggeringItem.name+"_Override", "ON")
}
end
// Theory of operation: If it is day time, turn on/off the weather lights when cloudy conditions
// change. Trigger the rule when it first becomes day so we can apply cloudy to lights then as well.
rule "Turn on lights when it is cloudy"
when
Item vIsCloudy changed or
Item vTimeOfDay changed to "DAY"
then
// We only care about daytime and vIsCloudy isn't NULL
if(vTimeOfDay.state != "DAY" || vIsCloudy.state == NULL) return;
// give the side effects of time of day time to complete
if(triggeringItem.name == "vTimeOfDay") Thread::sleep(500)
logInfo(logName, "It is " + vTimeOfDay.state.toString + " and cloudy changed: " + vIsCloudy.state.toString +", adjusting lighting")
// Apply the cloudy state to all the lights in the weather group
gLights_ON_WEATHER.members.forEach[ SwitchItem l |
val overrideName = l.name+"_Override"
val override = gLights_WEATHER_OVERRIDE.members.findFirst[ o | o.name == overrideName ]
if(override.state != ON && l.state != vIsCloudy.state) l.sendCommand(vIsCloudy.state as OnOffType)
if(override.state == ON) logInfo(logName, l.name + " is overridden")
]
end
At a high level, any change to the light that takes place 5 seconds or more after a schedule/expected state change is treated as an override of the usual Rule behavior.