]> git.basschouten.com Git - openhab-addons.git/commitdiff
Added humidity channel, minor fixes (#9467)
authorChristoph Weitkamp <github@christophweitkamp.de>
Tue, 22 Dec 2020 19:55:08 +0000 (20:55 +0100)
committerGitHub <noreply@github.com>
Tue, 22 Dec 2020 19:55:08 +0000 (20:55 +0100)
Signed-off-by: Christoph Weitkamp <github@christophweitkamp.de>
bundles/org.openhab.binding.avmfritz/README.md
bundles/org.openhab.binding.avmfritz/src/main/java/org/openhab/binding/avmfritz/internal/AVMFritzBindingConstants.java
bundles/org.openhab.binding.avmfritz/src/main/java/org/openhab/binding/avmfritz/internal/dto/AVMFritzBaseModel.java
bundles/org.openhab.binding.avmfritz/src/main/java/org/openhab/binding/avmfritz/internal/dto/DeviceModel.java
bundles/org.openhab.binding.avmfritz/src/main/java/org/openhab/binding/avmfritz/internal/dto/HumidityModel.java [new file with mode: 0644]
bundles/org.openhab.binding.avmfritz/src/main/java/org/openhab/binding/avmfritz/internal/handler/AVMFritzBaseThingHandler.java
bundles/org.openhab.binding.avmfritz/src/main/java/org/openhab/binding/avmfritz/internal/handler/AVMFritzButtonHandler.java
bundles/org.openhab.binding.avmfritz/src/main/resources/OH-INF/i18n/avmfritz_de.properties
bundles/org.openhab.binding.avmfritz/src/main/resources/OH-INF/thing/channel-types.xml
bundles/org.openhab.binding.avmfritz/src/test/java/org/openhab/binding/avmfritz/internal/dto/AVMFritzDeviceListModelTest.java

index 6799e8c2025ac48126f291a5c78151aa7e34e96c..8e5b88690202c16513f9bb3a858d5d1110020dda 100644 (file)
@@ -169,6 +169,7 @@ The AIN (actor identification number) can be found in the FRITZ!Box interface ->
 | locked          | Contact                  | Device is locked for switching over external sources (OPEN/CLOSE)                                                                                  | FRITZ!DECT 210, FRITZ!DECT 200, FRITZ!Powerline 546E, FRITZ!DECT 301, FRITZ!DECT 300, Comet DECT                    |
 | device_locked   | Contact                  | Device is locked for switching manually (OPEN/CLOSE) - FRITZ!OS 6.90                                                                               | FRITZ!DECT 210, FRITZ!DECT 200, FRITZ!Powerline 546E, FRITZ!DECT 301, FRITZ!DECT 300, Comet DECT                    |
 | temperature     | Number:Temperature       | Current measured temperature                                                                                                                       | FRITZ!DECT 210, FRITZ!DECT 200, FRITZ!DECT Repeater 100, FRITZ!DECT 301, FRITZ!DECT 300, Comet DECT, FRITZ!DECT 440 |
+| humidity        | Number:Dimensionless     | Current measured humidity - FRITZ!OS 7.24                                                                                                          | FRITZ!DECT 440                                                                                           |
 | energy          | Number:Energy            | Accumulated energy consumption                                                                                                                     | FRITZ!DECT 210, FRITZ!DECT 200, FRITZ!Powerline 546E                                                                |
 | power           | Number:Power             | Current power consumption                                                                                                                          | FRITZ!DECT 210, FRITZ!DECT 200, FRITZ!Powerline 546E                                                                |
 | voltage         | Number:ElectricPotential | Current voltage - FRITZ!OS 7                                                                                                                       | FRITZ!DECT 210, FRITZ!DECT 200, FRITZ!Powerline 546E                                                                |
index 0589c5e37fb5ee772c790dce2c649d0868962fe8..11ba9635a75dd801c5af8abdcc9a4e89bd1c2b32 100644 (file)
@@ -89,6 +89,7 @@ public class AVMFritzBindingConstants {
     public static final String PROPERTY_MEMBERS = "members";
 
     // List of all channel groups
+    public static final String CHANNEL_GROUP_SENSORS = "sensors";
     public static final String CHANNEL_GROUP_TOP_LEFT = "top-left";
     public static final String CHANNEL_GROUP_BOTTOM_LEFT = "bottom-left";
     public static final String CHANNEL_GROUP_TOP_RIGHT = "top-right";
@@ -105,6 +106,7 @@ public class AVMFritzBindingConstants {
     public static final String CHANNEL_DEVICE_LOCKED = "device_locked";
     public static final String CHANNEL_APPLY_TEMPLATE = "apply_template";
     public static final String CHANNEL_TEMPERATURE = "temperature";
+    public static final String CHANNEL_HUMIDITY = "humidity";
     public static final String CHANNEL_ENERGY = "energy";
     public static final String CHANNEL_POWER = "power";
     public static final String CHANNEL_VOLTAGE = "voltage";
index 4e8c2be1c2fd86fd429fa359c2301574019a9143..3a153cc61e4da5d65375828c30903a719ff0d6f5 100644 (file)
@@ -47,11 +47,12 @@ public abstract class AVMFritzBaseModel implements BatteryModel {
     protected static final int BUTTON_BIT = 1 << 5; // Bit 5
     protected static final int HEATING_THERMOSTAT_BIT = 1 << 6; // Bit 6
     protected static final int POWERMETER_BIT = 1 << 7; // Bit 7
-    protected static final int TEMPSENSOR_BIT = 1 << 8; // Bit 8
+    protected static final int TEMPERATURE_SENSOR_BIT = 1 << 8; // Bit 8
     protected static final int OUTLET_BIT = 1 << 9; // Bit 9
     protected static final int DECT_REPEATER_BIT = 1 << 10; // Bit 10
     protected static final int MICROPHONE_BIT = 1 << 11; // Bit 11
     protected static final int HAN_FUN_UNIT_BIT = 1 << 13; // Bit 13
+    protected static final int HUMIDITY_SENSOR_BIT = 1 << 20; // Bit 20 - undocumented
 
     @XmlAttribute(name = "identifier")
     private String ident;
@@ -149,7 +150,11 @@ public abstract class AVMFritzBaseModel implements BatteryModel {
     }
 
     public boolean isTempSensor() {
-        return (bitmask & TEMPSENSOR_BIT) > 0;
+        return (bitmask & TEMPERATURE_SENSOR_BIT) > 0;
+    }
+
+    public boolean isHumiditySensor() {
+        return (bitmask & HUMIDITY_SENSOR_BIT) > 0;
     }
 
     public boolean isPowermeter() {
@@ -208,13 +213,14 @@ public abstract class AVMFritzBaseModel implements BatteryModel {
                 .append(",isHANFUNDevice=").append(isHANFUNDevice()).append(",isHANFUNButton=").append(isHANFUNButton())
                 .append(",isHANFUNAlarmSensor=").append(isHANFUNAlarmSensor()).append(",isButton=").append(isButton())
                 .append(",isSwitchableOutlet=").append(isSwitchableOutlet()).append(",isTempSensor=")
-                .append(isTempSensor()).append(",isPowermeter=").append(isPowermeter()).append(",isDectRepeater=")
-                .append(isDectRepeater()).append(",isHeatingThermostat=").append(isHeatingThermostat())
-                .append(",isMicrophone=").append(isMicrophone()).append(",isHANFUNUnit=").append(isHANFUNUnit())
-                .append(",id=").append(deviceId).append(",manufacturer=").append(deviceManufacturer)
-                .append(",productname=").append(productName).append(",fwversion=").append(firmwareVersion)
-                .append(",present=").append(present).append(",name=").append(name).append(",battery=")
-                .append(getBattery()).append(",batterylow=").append(getBatterylow()).append(",").append(getSwitch())
-                .append(",").append(getPowermeter()).append(",").append(getHkr()).append(",").toString();
+                .append(isTempSensor()).append(",isHumiditySensor=").append(isHumiditySensor()).append(",isPowermeter=")
+                .append(isPowermeter()).append(",isDectRepeater=").append(isDectRepeater())
+                .append(",isHeatingThermostat=").append(isHeatingThermostat()).append(",isMicrophone=")
+                .append(isMicrophone()).append(",isHANFUNUnit=").append(isHANFUNUnit()).append(",id=").append(deviceId)
+                .append(",manufacturer=").append(deviceManufacturer).append(",productname=").append(productName)
+                .append(",fwversion=").append(firmwareVersion).append(",present=").append(present).append(",name=")
+                .append(name).append(",battery=").append(getBattery()).append(",batterylow=").append(getBatterylow())
+                .append(",").append(getSwitch()).append(",").append(getPowermeter()).append(",").append(getHkr())
+                .append(",").toString();
     }
 }
index 56c571a9cd67d8b1ba06d5dd9b0e51fa41b27668..5421a912f4de8b69d0f15bbadbd14fad38286246 100644 (file)
@@ -12,7 +12,6 @@
  */
 package org.openhab.binding.avmfritz.internal.dto;
 
-import java.util.Collections;
 import java.util.List;
 
 import javax.xml.bind.annotation.XmlAccessType;
@@ -31,6 +30,7 @@ import javax.xml.bind.annotation.XmlType;
 public class DeviceModel extends AVMFritzBaseModel {
 
     private TemperatureModel temperature;
+    private HumidityModel humidity;
     private AlertModel alert;
 
     @XmlElement(name = "button", type = ButtonModel.class)
@@ -46,6 +46,14 @@ public class DeviceModel extends AVMFritzBaseModel {
         this.temperature = temperatureModel;
     }
 
+    public HumidityModel getHumidity() {
+        return humidity;
+    }
+
+    public void setTemperature(HumidityModel humidityModel) {
+        this.humidity = humidityModel;
+    }
+
     public AlertModel getAlert() {
         return alert;
     }
@@ -55,10 +63,7 @@ public class DeviceModel extends AVMFritzBaseModel {
     }
 
     public List<ButtonModel> getButtons() {
-        if (buttons == null) {
-            return Collections.emptyList();
-        }
-        return buttons;
+        return buttons == null ? List.of() : buttons;
     }
 
     public void setButtons(List<ButtonModel> buttons) {
@@ -75,8 +80,8 @@ public class DeviceModel extends AVMFritzBaseModel {
 
     @Override
     public String toString() {
-        return new StringBuilder().append(super.toString()).append(temperature).append(",").append(alert).append(",")
-                .append(getButtons()).append(",").append(etsiunitinfo).append("]").toString();
+        return new StringBuilder().append(super.toString()).append(temperature).append(",").append(humidity).append(",")
+                .append(alert).append(",").append(getButtons()).append(",").append(etsiunitinfo).append("]").toString();
     }
 
     @XmlAccessorType(XmlAccessType.FIELD)
diff --git a/bundles/org.openhab.binding.avmfritz/src/main/java/org/openhab/binding/avmfritz/internal/dto/HumidityModel.java b/bundles/org.openhab.binding.avmfritz/src/main/java/org/openhab/binding/avmfritz/internal/dto/HumidityModel.java
new file mode 100644 (file)
index 0000000..bd1b553
--- /dev/null
@@ -0,0 +1,46 @@
+/**
+ * Copyright (c) 2010-2020 Contributors to the openHAB project
+ *
+ * See the NOTICE file(s) distributed with this work for additional
+ * information.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License 2.0 which is available at
+ * http://www.eclipse.org/legal/epl-2.0
+ *
+ * SPDX-License-Identifier: EPL-2.0
+ */
+package org.openhab.binding.avmfritz.internal.dto;
+
+import java.math.BigDecimal;
+
+import javax.xml.bind.annotation.XmlAccessType;
+import javax.xml.bind.annotation.XmlAccessorType;
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlRootElement;
+
+/**
+ * See {@link DeviceListModel}.
+ *
+ * @author Christoph Weitkamp - Initial contribution
+ */
+@XmlAccessorType(XmlAccessType.FIELD)
+@XmlRootElement(name = "humidity")
+public class HumidityModel {
+
+    @XmlElement(name = "rel_humidity")
+    private BigDecimal relativeHumidity;
+
+    public BigDecimal getRelativeHumidity() {
+        return relativeHumidity != null ? relativeHumidity : BigDecimal.ZERO;
+    }
+
+    public void setRelativeHumidity(BigDecimal relativeHumidity) {
+        this.relativeHumidity = relativeHumidity;
+    }
+
+    @Override
+    public String toString() {
+        return new StringBuilder().append("[rel_humidity=").append(getRelativeHumidity()).append("]").toString();
+    }
+}
index 92fa22c391574d94b61aaee8bc5afd8bd68b3f80..371b3960d2740e2c38ee3da369a32ded4cc691bd 100644 (file)
@@ -32,6 +32,7 @@ import org.openhab.binding.avmfritz.internal.dto.BatteryModel;
 import org.openhab.binding.avmfritz.internal.dto.DeviceModel;
 import org.openhab.binding.avmfritz.internal.dto.HeatingModel;
 import org.openhab.binding.avmfritz.internal.dto.HeatingModel.NextChangeModel;
+import org.openhab.binding.avmfritz.internal.dto.HumidityModel;
 import org.openhab.binding.avmfritz.internal.dto.PowerMeterModel;
 import org.openhab.binding.avmfritz.internal.dto.SwitchModel;
 import org.openhab.binding.avmfritz.internal.dto.TemperatureModel;
@@ -138,6 +139,9 @@ public abstract class AVMFritzBaseThingHandler extends BaseThingHandler implemen
                 if (deviceModel.isTempSensor()) {
                     updateTemperatureSensor(deviceModel.getTemperature());
                 }
+                if (deviceModel.isHumiditySensor()) {
+                    updateHumiditySensor(deviceModel.getHumidity());
+                }
                 if (deviceModel.isHANFUNAlarmSensor()) {
                     updateHANFUNAlarmSensor(deviceModel.getAlert());
                 }
@@ -161,6 +165,13 @@ public abstract class AVMFritzBaseThingHandler extends BaseThingHandler implemen
         }
     }
 
+    protected void updateHumiditySensor(@Nullable HumidityModel humidityModel) {
+        if (humidityModel != null) {
+            updateThingChannelState(CHANNEL_HUMIDITY,
+                    new QuantityType<>(humidityModel.getRelativeHumidity(), Units.PERCENT));
+        }
+    }
+
     private void updateHeatingThermostat(@Nullable HeatingModel heatingModel) {
         if (heatingModel != null) {
             updateThingChannelState(CHANNEL_MODE, new StringType(heatingModel.getMode()));
@@ -255,6 +266,19 @@ public abstract class AVMFritzBaseThingHandler extends BaseThingHandler implemen
         }
     }
 
+    /**
+     * Creates a {@link ChannelTypeUID} from the given channel id.
+     *
+     * @param channelId ID of the channel type UID to be created.
+     * @return the channel type UID
+     */
+    private ChannelTypeUID createChannelTypeUID(String channelId) {
+        int pos = channelId.indexOf(ChannelUID.CHANNEL_GROUP_SEPARATOR);
+        String id = pos > -1 ? channelId.substring(pos + 1) : channelId;
+        return CHANNEL_BATTERY.equals(id) ? DefaultSystemChannelTypeProvider.SYSTEM_CHANNEL_BATTERY_LEVEL.getUID()
+                : new ChannelTypeUID(BINDING_ID, id);
+    }
+
     /**
      * Creates new channels for the thing.
      *
@@ -264,9 +288,7 @@ public abstract class AVMFritzBaseThingHandler extends BaseThingHandler implemen
         ThingHandlerCallback callback = getCallback();
         if (callback != null) {
             ChannelUID channelUID = new ChannelUID(thing.getUID(), channelId);
-            ChannelTypeUID channelTypeUID = CHANNEL_BATTERY.equals(channelId)
-                    ? DefaultSystemChannelTypeProvider.SYSTEM_CHANNEL_BATTERY_LEVEL.getUID()
-                    : new ChannelTypeUID(BINDING_ID, channelId);
+            ChannelTypeUID channelTypeUID = createChannelTypeUID(channelId);
             Channel channel = callback.createChannelBuilder(channelUID, channelTypeUID).build();
             updateThing(editThing().withoutChannel(channelUID).withChannel(channel).build());
         }
@@ -317,6 +339,7 @@ public abstract class AVMFritzBaseThingHandler extends BaseThingHandler implemen
             case CHANNEL_LOCKED:
             case CHANNEL_DEVICE_LOCKED:
             case CHANNEL_TEMPERATURE:
+            case CHANNEL_HUMIDITY:
             case CHANNEL_ENERGY:
             case CHANNEL_POWER:
             case CHANNEL_VOLTAGE:
index d8d681794cf55d1730bf3cda9d275bdd78c79e9f..6e5afdc57150ec5e093161c9cb95533009f722f6 100644 (file)
@@ -25,7 +25,10 @@ import org.eclipse.jdt.annotation.Nullable;
 import org.openhab.binding.avmfritz.internal.dto.AVMFritzBaseModel;
 import org.openhab.binding.avmfritz.internal.dto.ButtonModel;
 import org.openhab.binding.avmfritz.internal.dto.DeviceModel;
+import org.openhab.binding.avmfritz.internal.dto.HumidityModel;
 import org.openhab.core.library.types.DateTimeType;
+import org.openhab.core.library.types.QuantityType;
+import org.openhab.core.library.unit.Units;
 import org.openhab.core.thing.Channel;
 import org.openhab.core.thing.ChannelUID;
 import org.openhab.core.thing.CommonTriggerEvents;
@@ -86,6 +89,14 @@ public class AVMFritzButtonHandler extends DeviceHandler {
         }
     }
 
+    @Override
+    protected void updateHumiditySensor(@Nullable HumidityModel humidityModel) {
+        if (humidityModel != null) {
+            updateThingChannelState(CHANNEL_GROUP_SENSORS + ChannelUID.CHANNEL_GROUP_SEPARATOR + CHANNEL_HUMIDITY,
+                    new QuantityType<>(humidityModel.getRelativeHumidity(), Units.PERCENT));
+        }
+    }
+
     private void updateShortLongPressButton(List<ButtonModel> buttons) {
         ButtonModel shortPressButton = buttons.size() > 0 ? buttons.get(0) : null;
         ButtonModel longPressButton = buttons.size() > 1 ? buttons.get(1) : null;
index a006fc748f2773aa05f6925b6cd9c6cecda7916f..d8728b93cf13c6950f6c827e26c99e04c539c167 100644 (file)
@@ -159,6 +159,9 @@ channel-type.avmfritz.apply_template.description = Erm
 channel-type.avmfritz.temperature.label = Temperatur
 channel-type.avmfritz.temperature.description = Zeigt die aktuelle Temperatur an.
 
+channel-type.avmfritz.humidity.label = Luftfeuchtigkeit
+channel-type.avmfritz.humidity.description = Zeigt die aktuelle Luftfeuchtigkeit an.
+
 channel-type.avmfritz.energy.label = Gesamtverbrauch
 channel-type.avmfritz.energy.description = Zeigt den akkumulierten Gesamtverbrauch an.
 
index 410d7ca60e9bc0110c54fc4fe31c61c1b08889b8..bcaf60c729afb9f094b1af5d50d7b048b1c141e3 100644 (file)
@@ -97,6 +97,7 @@
                <label>Sensor Data</label>
                <channels>
                        <channel id="temperature" typeId="temperature"/>
+                       <channel id="humidity" typeId="humidity"/>
                </channels>
        </channel-group-type>
 
                <config-description-ref uri="channel-type:avmfritz:temperature"/>
        </channel-type>
 
+       <channel-type id="humidity">
+               <item-type>Number:Dimensionless</item-type>
+               <label>Current Humidity</label>
+               <description>Current measured humidity.</description>
+               <category>Humidity</category>
+               <state pattern="%.0f %unit%" readOnly="true"/>
+       </channel-type>
+
        <channel-type id="energy">
                <item-type>Number:Energy</item-type>
                <label>Energy Consumption</label>
index 045d7ec9eeb68bf28cee4c95db5ba956df170fad..39aa45e9f0f0e73a2270b63bbca249d3fe236c46 100644 (file)
@@ -58,7 +58,7 @@ public class AVMFritzDeviceListModelTest {
                     "<device identifier=\"11934 0059978-1\" id=\"2000\" functionbitmask=\"8208\" fwversion=\"0.0\" manufacturer=\"0x0feb\" productname=\"HAN-FUN\"><present>0</present><name>HAN-FUN #2: Unit #2</name><etsiunitinfo><etsideviceid>406</etsideviceid><unittype>514</unittype><interfaces>256</interfaces></etsiunitinfo><alert><state>1</state></alert></device>" +
                     "<device identifier=\"11934 0059979-1\" id=\"2001\" functionbitmask=\"8200\" fwversion=\"0.0\" manufacturer=\"0x0feb\" productname=\"HAN-FUN\"><present>0</present><name>HAN-FUN #2: Unit #2</name><etsiunitinfo><etsideviceid>412</etsideviceid><unittype>273</unittype><interfaces>772</interfaces></etsiunitinfo><button><lastpressedtimestamp>1529590797</lastpressedtimestamp></button></device>" +
                     "<device identifier=\"13096 0007307\" id=\"29\" functionbitmask=\"32\" fwversion=\"04.90\" manufacturer=\"AVM\" productname=\"FRITZ!DECT 400\"><present>1</present><name>FRITZ!DECT 400 #14</name><battery>100</battery><batterylow>0</batterylow><button identifier=\"13096 0007307-0\" id=\"5000\"><name>FRITZ!DECT 400 #14: kurz</name><lastpressedtimestamp>1549195586</lastpressedtimestamp></button><button identifier=\"13096 0007307-9\" id=\"5001\"><name>FRITZ!DECT 400 #14: lang</name><lastpressedtimestamp>1549195595</lastpressedtimestamp></button></device>" +
-                    "<device identifier=\"13096 0007308\" id=\"30\" functionbitmask=\"288\" fwversion=\"04.90\" manufacturer=\"AVM\" productname=\"FRITZ!DECT 440\"><present>1</present><name>FRITZ!DECT 440 #15</name><temperature><celsius>230</celsius><offset>0</offset></temperature><battery>100</battery><batterylow>0</batterylow><button identifier=\"13096 0007308-1\" id=\"5000\"><name>FRITZ!DECT 440 #15: Oben rechts</name><lastpressedtimestamp>1549195586</lastpressedtimestamp></button><button identifier=\"13096 0007308-3\" id=\"5001\"><name>FRITZ!DECT 440 #15: Unten rechts</name><lastpressedtimestamp>1549195595</lastpressedtimestamp></button><button identifier=\"13096 0007308-5\" id=\"5002\"><name>FRITZ!DECT 440 #15: Unten links</name><lastpressedtimestamp>1549195586</lastpressedtimestamp></button><button identifier=\"13096 0007308-7\" id=\"5003\"><name>FRITZ!DECT 440 #15: Oben links</name><lastpressedtimestamp>1549195595</lastpressedtimestamp></button></device>" +
+                    "<device identifier=\"13096 0007308\" id=\"30\" functionbitmask=\"1048864\" fwversion=\"05.10\" manufacturer=\"AVM\" productname=\"FRITZ!DECT 440\"><present>1</present><name>FRITZ!DECT 440 #15</name><temperature><celsius>230</celsius><offset>0</offset></temperature><humidity><rel_humidity>43</rel_humidity></humidity><battery>100</battery><batterylow>0</batterylow><button identifier=\"13096 0007308-1\" id=\"5000\"><name>FRITZ!DECT 440 #15: Oben rechts</name><lastpressedtimestamp>1549195586</lastpressedtimestamp></button><button identifier=\"13096 0007308-3\" id=\"5001\"><name>FRITZ!DECT 440 #15: Unten rechts</name><lastpressedtimestamp>1549195595</lastpressedtimestamp></button><button identifier=\"13096 0007308-5\" id=\"5002\"><name>FRITZ!DECT 440 #15: Unten links</name><lastpressedtimestamp>1549195586</lastpressedtimestamp></button><button identifier=\"13096 0007308-7\" id=\"5003\"><name>FRITZ!DECT 440 #15: Oben links</name><lastpressedtimestamp>1549195595</lastpressedtimestamp></button></device>" +
                 "</devicelist>";
         //@formatter:off
         try {
@@ -98,6 +98,7 @@ public class AVMFritzDeviceListModelTest {
         assertTrue(device.isDectRepeater());
         assertFalse(device.isSwitchableOutlet());
         assertTrue(device.isTempSensor());
+        assertFalse(device.isHumiditySensor());
         assertFalse(device.isPowermeter());
         assertFalse(device.isHeatingThermostat());
 
@@ -134,6 +135,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(device.isDectRepeater());
         assertTrue(device.isSwitchableOutlet());
         assertTrue(device.isTempSensor());
+        assertFalse(device.isHumiditySensor());
         assertTrue(device.isPowermeter());
         assertFalse(device.isHeatingThermostat());
 
@@ -174,6 +176,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(device.isDectRepeater());
         assertTrue(device.isSwitchableOutlet());
         assertTrue(device.isTempSensor());
+        assertFalse(device.isHumiditySensor());
         assertTrue(device.isPowermeter());
         assertFalse(device.isHeatingThermostat());
 
@@ -214,6 +217,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(device.isDectRepeater());
         assertFalse(device.isSwitchableOutlet());
         assertTrue(device.isTempSensor());
+        assertFalse(device.isHumiditySensor());
         assertFalse(device.isPowermeter());
         assertTrue(device.isHeatingThermostat());
 
@@ -250,6 +254,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(device.isDectRepeater());
         assertFalse(device.isSwitchableOutlet());
         assertTrue(device.isTempSensor());
+        assertFalse(device.isHumiditySensor());
         assertFalse(device.isPowermeter());
         assertTrue(device.isHeatingThermostat());
 
@@ -286,6 +291,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(device.isDectRepeater());
         assertFalse(device.isSwitchableOutlet());
         assertTrue(device.isTempSensor());
+        assertFalse(device.isHumiditySensor());
         assertFalse(device.isPowermeter());
         assertTrue(device.isHeatingThermostat());
 
@@ -322,6 +328,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(device.isDectRepeater());
         assertFalse(device.isSwitchableOutlet());
         assertFalse(device.isTempSensor());
+        assertFalse(device.isHumiditySensor());
         assertFalse(device.isPowermeter());
         assertFalse(device.isHeatingThermostat());
 
@@ -355,7 +362,7 @@ public class AVMFritzDeviceListModelTest {
         assertEquals("FRITZ!DECT 440", device.getProductName());
         assertEquals("130960007308", device.getIdentifier());
         assertEquals("30", device.getDeviceId());
-        assertEquals("04.90", device.getFirmwareVersion());
+        assertEquals("05.10", device.getFirmwareVersion());
         assertEquals("AVM", device.getManufacturer());
 
         assertEquals(1, device.getPresent());
@@ -367,6 +374,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(device.isDectRepeater());
         assertFalse(device.isSwitchableOutlet());
         assertTrue(device.isTempSensor());
+        assertTrue(device.isHumiditySensor());
         assertFalse(device.isPowermeter());
         assertFalse(device.isHeatingThermostat());
 
@@ -403,6 +411,9 @@ public class AVMFritzDeviceListModelTest {
         assertEquals(new BigDecimal("23.0"), device.getTemperature().getCelsius());
         assertEquals(new BigDecimal("0.0"), device.getTemperature().getOffset());
 
+        assertNotNull(device.getHumidity());
+        assertEquals(new BigDecimal("43"), device.getHumidity().getRelativeHumidity());
+
         assertNull(device.getPowermeter());
 
         assertNull(device.getHkr());
@@ -430,6 +441,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(device.isDectRepeater());
         assertTrue(device.isSwitchableOutlet());
         assertFalse(device.isTempSensor());
+        assertFalse(device.isHumiditySensor());
         assertTrue(device.isPowermeter());
         assertFalse(device.isHeatingThermostat());
 
@@ -468,6 +480,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(device.isDectRepeater());
         assertFalse(device.isSwitchableOutlet());
         assertFalse(device.isTempSensor());
+        assertFalse(device.isHumiditySensor());
         assertFalse(device.isPowermeter());
         assertFalse(device.isHeatingThermostat());
 
@@ -507,6 +520,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(device.isDectRepeater());
         assertFalse(device.isSwitchableOutlet());
         assertFalse(device.isTempSensor());
+        assertFalse(device.isHumiditySensor());
         assertFalse(device.isPowermeter());
         assertFalse(device.isHeatingThermostat());
 
@@ -546,6 +560,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(group.isDectRepeater());
         assertFalse(group.isSwitchableOutlet());
         assertFalse(group.isTempSensor());
+        assertFalse(group.isHumiditySensor());
         assertFalse(group.isPowermeter());
         assertTrue(group.isHeatingThermostat());
 
@@ -582,6 +597,7 @@ public class AVMFritzDeviceListModelTest {
         assertFalse(group.isDectRepeater());
         assertTrue(group.isSwitchableOutlet());
         assertFalse(group.isTempSensor());
+        assertFalse(group.isHumiditySensor());
         assertTrue(group.isPowermeter());
         assertFalse(group.isHeatingThermostat());