Trigger every x seconds set using a variable - Possible in HE?

When the Central Heating is on I need check the status of a Thermostat Controller Operating State every 2 minutes.

Ideally I would just trigger off a changed state

Operating state of Thermostat Controller Kitchen changed

But that fails, too often so have to augment with a check every 2 minutes.

Is there a way to

a. Get Operating state of Thermostat Controller Kitchen changed reliable
b. Set the check period using variable so I can set it to 2 minutes when Central Heating Active and massively long when not
c. Better just to Pause the Rule when heating is disabled?


Is it possible to make a series of TRIGGER EVENTS AND rather than the default OR?

No, that is not how Triggers are used by RM. A Trigger is simply an event that wakes up a rule, and causes it to run its Actions. Those Actions can implement Conditions, that include checking for the status of multiple things using a variety of comparisons, as well are the ability to use AND /OR logic.


Why is it failing? Is the thermostat not reporting?

There is a new feature coming in the next release that would make your desired rule easier. But rather than poll the thermostat, it would be best to understand and remedy this failure.

1 Like

Why do you need changed? May I suggest that you create two rules, one for each of the desired states instead of changed, at least until you get this sorted out. If the thermostat is simply not reporting its operating state reliably, then what makes you think that asking for the operating state is reliable? Look at the device Events for it from its device page. Post a screenshot of that here.

1 Like


I have ~8 Thermostat Controller Apps - when the room/zone Thermostat Controller app status changes to Heat the rule will send explicit valve setting instructions to the Thermostatic Radiator Valve on the room radiator.

Triggering off just the Status = heat is very sporadic, sometimes it works but far too often it does not get triggered, so the room remains cold.

Hence the need to check every two minutes.

This is using the built in Thermostat Controller app, one for each zone/room.

I would extremely pleased to be able to get a rule to trigger reliably :smile:

Look at the events for the Controller thermostat, and post those here. From its device page Events button at top.

Whenever heating kicks in, it sends the Operating State event. So perhaps your problem has to do with what is driving Thermostat Controller, not the controller thermostat. Where does it get its temperatures? When you say "check every 2 minutes", what are you checking? What device?

You should post a screenshot of one of these Thermostat Controller setups.

Why are you using Thermostat Controller? It's not controlling a thermostat, from your description. Perhaps what you need is a Virtual Thermostat instead. Thermostat Controller is intended to control another thermostat, not what you're doing as far as your description goes. Is there another thermostat involved?

Temperature comes into the Thermostat Controller app

The Thermostat Controller app Sets the room/zone target temp

The Thermostat Controller app sets a virtual TRV to heat or idle when the room hits temp or falls below it.

Is this what you need?

So you are using Thermostat Controller to control a virtual thermostat, with two temperature sources -- Thermostat Controller is itself not a source of temperature.

I'm not sure what to tell you about this setup other than that it is highly convoluted, and hence hard to know what is going on and evidently prone to unexpected outcomes. This is probably not the way to go about this. Perhaps you should describe in words, instead of apps and virtual devices, how the heat is supposed to be controlled. Usually it's as simple as "when temperature drops below X, turn on heat, and when it rises to Y, turn off the heat".

Except for the fact that you have two temperature sources, is there some other reason you would use Thermostat Controller? Why not just use the Virtual TRV thermostat to do the same thing? Aren't you just taking events from these virtual devices and running rules from them? Does the Virtual TRV thermostat support a setTemperature() command? Does it actually model a thermostat, with setpoints and operating states? Why are you using it, and for what?

I do not disagree with you :slight_smile:

This is a 8 zone/room heating system, with -10 independently controllable radiators each with a zwave thermostatic valve. (Exception there are another 5 radiators that are using basic non smart valve and one that is totally unrestricted (a requirement for the boiler))

The boiler is a zwave dual channel switch.

The thermostatic radiator valves are zwave eurotonic.

I use a built in Thermostat Controller app for each radiator, a built in Thermostat scheduler manages each room/zone.

A room/zone has one or two radiators.

Because the eurotronic TRVs require direct control of the valve it requires extra control.

So each room has a built in Thermostat Scheduler to manage target temps as the house switches from one mode to another.

The Thermostat Scheduler sets the target temperatures in the built in Thermostat Controller app

The Thermostat Controller App is monitoring two temp sensors, one zigbee the other zwave, and compares the average of these against the target setpoint.

If the current temp is below the target then the Thermostat Controller sends Heating status to the connected TRV.

Ideally the connected TRV would be the zwave TRV, but from multiple years of working with these zwave eurotronic TRVs are extremely reliable only if under direct valve control.

The built in Thermostat Controller cannot directly drive the TRV valve, at least I have not found a way.

So I am required to create a virtual TRV that the Thermostat Controller can control.

Then detect when the Thermostat Controller has placed the virtual TRV into ‘heating’ and send a direct valve control to the zwave TRV.

If there is a better way to have a scheduler, Thermostat Controller and directly control of the zwave TRV valve I will be very very :grinning:

I believe the way out of your mess is to use a single virtual thermostat device, modified to control your TRV valves instead of using Thermostat Controller. Problem is there is just too much complexity the way you're doing it.

I think we will publish a generic Virtual Thermostat driver in our public repo. I'll do this in the next day or two. This driver could be modified as needed. The virtual thermostat device itself could be used in Thermostat Scheduler, and Thermostat Controller would not be part of the mix at all. For using an average temperature of multiple sensors, you could use the published Average Temp app and use it to set the temperature of the virtual thermostat (instead of creating a virtual temperature device).

1 Like

This may help.

Anything that allows me to simplify is good.

Each room/zone has its own setpoint that changes with each house mode, and changes depending on Summer/ Holiday and Guest modes.

So an inherent level of complexity is to be expected.

The whole HE hub is dedicated to this and hot water management, everything else is operated on another HE hub.


Thanks, my skills are lacking in tweaking this.

I’ll try and think of a way to simplify it.

It has been extremely reliable apart from the last update that broke the rules, but was easily remedied by recreating the exact same rules again.

I have had to recreate the same rule twice after an update, so know to expect it now :slight_smile:

You don't need to. If you're using a rule fired by thermostat operating state, this virtual thermostat will send out those events for you to trigger those rules. For instance, it will set the operating state to "heating" or "idle" as indicated by the setpoint and the temperature.

All you have to do is use Average Temp app to set the temperature from your sensors. Below is a modified version of that app that allows you to select the virtual thermostat to push temperature into. That's all there is to it.

    name: "Average Temperatures",
    namespace: "hubitat",
    author: "Bruce Ravenel",
    description: "Average some temperature sensors",
    category: "Convenience",
    iconUrl: "",
    iconX2Url: "")

preferences {
	page(name: "mainPage")

def mainPage() {
	dynamicPage(name: "mainPage", title: " ", install: true, uninstall: true) {
		section {
			input "thisName", "text", title: "Name this temperature averager", submitOnChange: true
			if(thisName) app.updateLabel("$thisName")
            input "averageDev", "capability.thermostat", title: "Select virtual thermostat", submitOnChange: true
			input "tempSensors", "capability.temperatureMeasurement", title: "Select Temperature Sensors", submitOnChange: true, required: true, multiple: true
			paragraph "Enter weight factors and offsets"
			tempSensors.each {
				input "weight$", "decimal", title: "$it ($it.currentTemperature)", defaultValue: 1.0, submitOnChange: true, width: 3
				input "offset$", "decimal", title: "$it Offset", defaultValue: 0.0, submitOnChange: true, range: "*..*", width: 3
			input "useRun", "number", title: "Compute running average over this many sensor events:", defaultValue: 1, submitOnChange: true
			if(tempSensors) paragraph "Current sensor average is ${averageTemp()}°"
			if(useRun > 1) {
				if(tempSensors) paragraph "Current running average is ${averageTemp(useRun)}°"

def installed() {

def updated() {

def initialize() {
//    	def averageDev = getChildDevice("AverageTemp_${}")
//    	if(!averageDev) averageDev = addChildDevice("hubitat", "Virtual Temperature Sensor", "AverageTemp_${}", null, [label: thisName, name: thisName])
	subscribe(tempSensors, "temperature", handler)

def initRun() {
	def temp = averageTemp()
	if(! { = []
		for(int i = 0; i < useRun; i++) += temp

def averageTemp(run = 1) {
	def total = 0
	def n = 0
	tempSensors.each {
		def offset = settings["offset$"] != null ? settings["offset$"] : 0
		total += (it.currentTemperature + offset) * (settings["weight$"] != null ? settings["weight$"] : 1)
		n += settings["weight$"] != null ? settings["weight$"] : 1
	def result = total / (n = 0 ? tempSensors.size() : n)
	if(run > 1) {
		total = 0 {total += it}
		result = total / run
	return result.toDouble().round(1)

def handler(evt) {
//    	def averageDev = getChildDevice("AverageTemp_${}")
	def avg = averageTemp()
	if(useRun > 1) { = + avg
		avg = averageTemp(useRun)
	averageDev.setTemperature(avg) "Average sensor temperature = ${averageTemp()}°" + (useRun > 1 ? "    Running average is $avg°" : "")

Many thanks for this, I don’t understand yet, how this will streamline things, but will look at setting it up and testing it

So this is what I think is how to use the new Virtual Thermostat device and Average Temperatures app.

Is there a simpler way in HE?

Realistically - I can just use the Zwave Temp Sensors directly and run from the MASTER HE a sanity check for each zwave sensor against the zigbee temp sensor in each room - if there is a discrepancy then raise an alert.

Probably no reason to have BOTH involved directly in heating, just use them as a sanity check.

That will simply it a bit more

I can also reduce number of Thermostat Schedulers, now I have been using them for 7 months I know I can combine Guest Bedrooms and Guest Bathrooms in to just 2 Schedulers as they have same set points and will adjust depending on Guest Mode activation.

Actually given the above - I can simplify for 8 of the zones further by using the Secure SRT321 directly as Thermostats instead of just Temp Sensors - simplifying it further.

The SRTs can get a battery hungry - but have resolved that largely by using USB powered battery eliminators.

I'll look at a way of tracking the ThermostatOperatingstate directly rather than using variables, that will simplify it down further.

Simplified version - v4.

I have 10 zones/rooms.

Guest Mode and Backdoor Open impacts specific rooms, that I have to document separately.

In this version the exceptions are managed at the Boiler, I could ALSO catch them at the Rule that manages the Valve levels too. I suspect it will add complexity for little return as all the Valves are on Battery Eliminators.

I'm still a big WebCore user because I've used it for so long, know it best and still trying to figure out how to do this with RM. Thankfully WebCore is a Built-In App now. I created a Virtual Temperature Sensor and made a Piston that does an Average of my in home temperature sensors every 30 minutes.