]> git.basschouten.com Git - openhab-addons.git/commitdiff
[knx] Fix IOOB exception with missing DPT in number channels (#15730)
authorJ-N-K <github@klug.nrw>
Wed, 6 Dec 2023 06:53:16 +0000 (07:53 +0100)
committerGitHub <noreply@github.com>
Wed, 6 Dec 2023 06:53:16 +0000 (07:53 +0100)
* Fix IOOB exception with missing DPT in number channels

Also improves test messages for DPT unit tests

Signed-off-by: Jan N. Klug <github@klug.nrw>
Co-authored-by: Holger Friedrich <mail@holger-friedrich.de>
bundles/org.openhab.binding.knx/src/main/java/org/openhab/binding/knx/internal/dpt/DPTUnits.java
bundles/org.openhab.binding.knx/src/main/java/org/openhab/binding/knx/internal/handler/DeviceThingHandler.java
bundles/org.openhab.binding.knx/src/test/java/org/openhab/binding/knx/internal/dpt/DPTTest.java

index a550f2027bf89131e7566a3eb1b6dbdf65934188..b7d43bed6c1797f53ef4e4f6ee269939c184cfe9 100644 (file)
@@ -63,8 +63,8 @@ public class DPTUnits {
      *
      * @return stream of all unit strings
      */
-    static Stream<String> getAllUnitStrings() {
-        return DPT_UNIT_MAP.values().stream();
+    static Stream<Map.Entry<String, String>> getAllUnitStrings() {
+        return DPT_UNIT_MAP.entrySet().stream();
     }
 
     static {
index 0f684320c4a838af85bf6dace2e1529d6dda3e0f..5c29712c8f182bc59c088152ebadd33cb1422718 100644 (file)
@@ -120,13 +120,16 @@ public class DeviceThingHandler extends BaseThingHandler implements GroupAddress
 
         for (Channel channel : getThing().getChannels()) {
             KNXChannel knxChannel = KNXChannelFactory.createKnxChannel(channel);
-            knxChannels.put(channel.getUID(), knxChannel);
-            groupAddresses.addAll(knxChannel.getAllGroupAddresses());
 
             if (knxChannel.getChannelType().startsWith("number")) {
                 // check if we need to update the accepted item-type
                 List<InboundSpec> inboundSpecs = knxChannel.getAllGroupAddresses().stream()
                         .map(knxChannel::getListenSpec).filter(Objects::nonNull).map(Objects::requireNonNull).toList();
+                if (inboundSpecs.isEmpty()) {
+                    logger.warn("Skipping {}: group address / DPT not according to Group Address Notation",
+                            channel.getUID());
+                    continue;
+                }
 
                 String dpt = inboundSpecs.get(0).getDPT(); // there can be only one DPT on number channels
                 Unit<?> unit = UnitUtils.parseUnit(DPTUnits.getUnitForDpt(dpt));
@@ -149,6 +152,10 @@ public class DeviceThingHandler extends BaseThingHandler implements GroupAddress
                     modified = true;
                 }
             }
+
+            // add channels only if they could be successfully processed
+            knxChannels.put(channel.getUID(), knxChannel);
+            groupAddresses.addAll(knxChannel.getAllGroupAddresses());
         }
 
         if (modified) {
index cda7f4c796c91a1ade4621e1e5771bdc0f367807..f969b265d65ced246d93be6705d6a6ec4305bf5f 100644 (file)
@@ -14,6 +14,7 @@ package org.openhab.binding.knx.internal.dpt;
 
 import static org.junit.jupiter.api.Assertions.*;
 
+import java.util.Map;
 import java.util.Objects;
 import java.util.regex.Matcher;
 import java.util.stream.IntStream;
@@ -386,16 +387,20 @@ class DPTTest {
         assertNotEquals(DPTXlator64BitSigned.DPT_REACTIVE_ENERGY.getUnit(), Units.VAR_HOUR.toString());
     }
 
-    private static Stream<String> unitProvider() {
+    private static Stream<Map.Entry<String, String>> unitProvider() {
         return DPTUnits.getAllUnitStrings();
     }
 
     @ParameterizedTest
     @MethodSource("unitProvider")
-    public void unitsValid(String unit) {
-        String valueStr = "1 " + unit;
-        QuantityType<?> value = new QuantityType<>(valueStr);
-        Assertions.assertNotNull(value);
+    public void unitsValid(Map.Entry<String, String> unit) {
+        String valueStr = "1 " + unit.getValue();
+        try {
+            QuantityType<?> value = new QuantityType<>(valueStr);
+            Assertions.assertNotNull(value, "Failed to parse " + unit + "(result null)");
+        } catch (Exception e) {
+            fail("Failed to parse " + unit + ": " + e.getMessage());
+        }
     }
 
     private static Stream<byte[]> rgbValueProvider() {