One Rule for many Temp/Humidity Things for absolute Humidity

Hi,
I have many Sensor Things for temperature and relative humidity

For these sensors I would like to create one Rule to calculate absolute humidity. The calculation works fine for one Rule on one Sensor, but I would like to unify the Rule for a group of sensors (=Things).

What is the best approach to do that in Xtend?

Can you elaborate on exactly what you want to do, e.g. what calculations are you going to perform? It’s ok to use pseudocode to demonstrate your thoughts

The calculation itself works fine. I’m looking for an idea to loop

pseudocode would be

on change Things ==“thermo_hydro_sensor” do

foreach (Things==“thermo_hydro_sensor” => th){
th.absHumidity = calcAbsHumidity(th.temperature,th.relhumidity)
}

Have you got your items created? If so, can you paste their definitions?

Assuming you have an item for abshum, temp and relhum, you could name them with a consistent naming scheme.

E.g.

Livingroom_abs_humidity
Livingroom_rel_humidity
Livingroom_temp

Then create a group called Absolute_Humidity and assign all the absolute humidity items to that group.

Then you’d loop through the members of this group. You can then use the naming scheme to access the other items (the corresponding relhum and temp items)

That’s one way of doing it easily in xtend/rulesdsl

Also instead of looping through all items, you could just trigger on changes like this:

import org.openhab.core.model.script.ScriptServiceUtil

rule "calculate abs humidity" 
when
  Member of Relative_Humidity changed
  Member of Temperature changed
then
  val ir = ScriptServiceUtil.itemRegistry

  name = triggeringItem.name.split("_")[0]
  rel_humidity = ir.getItem(name + "_rel_humidity").state as Number
  temp = ir.getItem(name + "_temperature").state as Number
  abs_humidity = calcAbsHumidity(temp, rel_humidity)
  postUpdate(name + "_abs_humidity", abs_humidity)
end

Another way is to use the semantic model but it’s harder to use that in rulesdsl than in, say, jruby.

I have temperature sensors added via zigbee2mqtt and created a custom transformation to calculate the drewpoint. By this you can move the calculation from item to thing definition and only need to maintain it once.
However that’s not working with all binding, mostly only mqtt, http or similar where you can customize channels

@Matze0211 - thanks to your post, I was reminded about never solving the absolute humidity puzzle.

I wanted to calculate absolute humidity, so I can compare humidity outdoor and indoor. This should allow me to create a “summer” mode for my heat recovery ventilation unit. The goal would be that the current “demand” mode is disabled in summertime when the air is too humid outside, which means that it’s not meaningful to run at high speed to try to lower the humidity inside.

I was not able to find a formula when I last looked at this problem, only some graphs. I tried again after reading your post, and found this:

So now I implemented this in JavaScript:

function calculateSaturationVaporPressure(temperature) {
    return 6.112 * Math.exp((17.67 * temperature) / (temperature + 243.5));
}

function calculateAbsoluteHumidity(relativeHumidity, temperature) {
    const saturationVaporPressure = calculateSaturationVaporPressure(temperature);
    const absoluteHumidity = (saturationVaporPressure * relativeHumidity * 2.1674) / (temperature + 273.15);
    return absoluteHumidity;
}

rules.when()
    .item("Netatmo_Carport_Humidity").changed()
    .or()
    .item("Netatmo_Carport_Temperature").changed()
    .then(event =>
    {
        var humidity = event.itemName == "Netatmo_Carport_Humidity" ? Quantity(event.newState) : items.Netatmo_Carport_Humidity.quantityState;
        var temperature = event.itemName == "Netatmo_Carport_Temperature" ? Quantity(event.newState) : items.Netatmo_Carport_Temperature.quantityState;
        var absoluteHumidity = calculateAbsoluteHumidity(humidity.toUnit("%").float, temperature.toUnit("°C").float);

        items.Netatmo_Carport_AbsoluteHumidity.postUpdate(absoluteHumidity + " g/m³");
    })
    .build("Calculate carport absolute humidity", "Calculate absolute humidity from relative humidity and temperature");

My question is: Is your calculation similar? I’d just like to verify if the implementation is correct.

That’s what I’m using.

The calculation is based on someones else recommendation I found a few years ago…

(function(i) {

	var json = JSON.parse(i);
	
    if(json.hasOwnProperty("temperature") && json.hasOwnProperty("humidity")) {
		var temp = json["temperature"];
		var hum = json["humidity"];
		if (temp >= 0.0){ 
			a = 7.5
			b = 237.3
		} else { 
			a = 7.6
			b = 240.7
		}

		SDD=(6.1078 * Math.pow(10.0, ((a*temp)/(b+temp))))
		DD = (hum/100.0*SDD)
		v = Math.log(DD/6.107) / 2.302585092994046
		result = ((b*v)/(a-v))
		result = result.toFixed(1);
		return result;
	}
	else {
		return "";
	}
})(input)
1 Like