diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/SmartMeterConfiguration.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/SmartMeterConfiguration.java index aefa13513e6..70fa7201819 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/SmartMeterConfiguration.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/SmartMeterConfiguration.java @@ -12,19 +12,25 @@ */ package org.openhab.binding.smartmeter; +import org.eclipse.jdt.annotation.NonNullByDefault; +import org.eclipse.jdt.annotation.Nullable; + /** * The {@link SmartMeterConfiguration} is the class used to match the * thing configuration. * * @author Matthias Steigenberger - Initial contribution */ +@NonNullByDefault public class SmartMeterConfiguration { + @Nullable public String port; - public Integer refresh; - public Integer baudrateChangeDelay; + public Integer refresh = 10; + public Integer baudrateChangeDelay = 0; + @Nullable public String initMessage; - public String baudrate; - public String mode; - public String conformity; + public String baudrate = "AUTO"; + public String mode = "SML"; + public String conformity = "NONE"; } diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterDevice.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterDevice.java index 3333f87b945..f69c32c72bc 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterDevice.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterDevice.java @@ -12,6 +12,7 @@ */ package org.openhab.binding.smartmeter.internal; +import java.io.IOException; import java.time.Duration; import java.util.ArrayList; import java.util.Collection; @@ -37,6 +38,7 @@ import org.slf4j.LoggerFactory; import io.reactivex.Flowable; import io.reactivex.disposables.Disposable; +import io.reactivex.exceptions.UndeliverableException; import io.reactivex.plugins.RxJavaPlugins; import io.reactivex.schedulers.Schedulers; @@ -83,7 +85,18 @@ public abstract class MeterDevice { this.connector = createConnector(serialPortManagerSupplier, serialPort, baudrate, baudrateChangeDelay, protocolMode); RxJavaPlugins.setErrorHandler(error -> { - logger.error("Fatal error occured", error); + if (error == null) { + logger.warn("Fatal but unknown error occurred"); + return; + } + if (error instanceof UndeliverableException) { + error = error.getCause(); + } + if (error instanceof IOException) { + logger.warn("Connection related issue occurred: {}", error.getMessage()); + return; + } + logger.warn("Fatal error occurred", error); }); } diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterDeviceFactory.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterDeviceFactory.java index 255d59094f4..51e8f2d5fad 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterDeviceFactory.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterDeviceFactory.java @@ -17,7 +17,7 @@ import java.util.function.Supplier; import org.eclipse.jdt.annotation.NonNullByDefault; import org.eclipse.jdt.annotation.Nullable; import org.openhab.binding.smartmeter.internal.helper.ProtocolMode; -import org.openhab.binding.smartmeter.internal.iec62056.Iec62056_21MeterReader; +import org.openhab.binding.smartmeter.internal.iec62056.MeterReader; import org.openhab.binding.smartmeter.internal.sml.SmlMeterReader; import org.openhab.core.io.transport.serial.SerialPortManager; @@ -49,8 +49,8 @@ public class MeterDeviceFactory { switch (protocolMode) { case D: case ABC: - return new Iec62056_21MeterReader(serialPortManagerSupplier, deviceId, serialPort, initMessage, - baudrate, baudrateChangeDelay, protocolMode); + return new MeterReader(serialPortManagerSupplier, deviceId, serialPort, initMessage, baudrate, + baudrateChangeDelay, protocolMode); case SML: return SmlMeterReader.createInstance(serialPortManagerSupplier, deviceId, serialPort, initMessage, baudrate, baudrateChangeDelay); diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterValue.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterValue.java index c93e939e28e..9c9dac6e539 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterValue.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/MeterValue.java @@ -66,11 +66,15 @@ public class MeterValue> { @Override public int hashCode() { final int prime = 31; + final String status = this.status; + final Unit unit = this.unit; + final String value = this.value; + int result = 1; - result = prime * result + ((obis == null) ? 0 : obis.hashCode()); - result = prime * result + ((status == null) ? 0 : status.hashCode()); - result = prime * result + ((unit == null) ? 0 : unit.hashCode()); - result = prime * result + ((value == null) ? 0 : value.hashCode()); + result = prime * result + obis.hashCode(); + result = prime * result + (status == null ? 0 : status.hashCode()); + result = prime * result + (unit == null ? 0 : unit.hashCode()); + result = prime * result + value.hashCode(); return result; } @@ -90,6 +94,7 @@ public class MeterValue> { if (!obis.equals(other.obis)) { return false; } + String status = this.status; if (status == null) { if (other.status != null) { return false; @@ -97,6 +102,7 @@ public class MeterValue> { } else if (!status.equals(other.status)) { return false; } + Unit unit = this.unit; if (unit == null) { if (other.unit != null) { return false; diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/ObisCode.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/ObisCode.java index c35e0f0498f..1e3a70a4c10 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/ObisCode.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/ObisCode.java @@ -82,6 +82,10 @@ public class ObisCode { * @return the obis as string. */ public String asDecimalString() { + Byte a = this.a; + Byte b = this.b; + Byte c = this.c; + Byte f = this.f; try (Formatter format = new Formatter()) { format.format(SmartMeterBindingConstants.OBIS_FORMAT, a != null ? a & 0xFF : 0, b != null ? b & 0xFF : 0, c & 0xFF, d & 0xFF, e & 0xFF, f != null ? f & 0xFF : 0); @@ -118,10 +122,15 @@ public class ObisCode { return asDecimalString(); } - public boolean matches(@Nullable Byte a, @Nullable Byte b, Byte c, Byte d, Byte e, @Nullable Byte f) { - return (this.a == null || a == null || this.a.equals(a)) && (this.b == null || b == null || this.b.equals(b)) - && this.c.equals(c) && this.d.equals(d) && this.e.equals(e) - && (this.f == null || f == null || this.f.equals(f)); + public boolean matches(@Nullable Byte otherA, @Nullable Byte otherB, Byte otherC, Byte d, Byte e, + @Nullable Byte otherF) { + Byte a = this.a; + Byte b = this.b; + Byte c = this.c; + Byte f = this.f; + return (a == null || otherA == null || a.equals(otherA)) && (b == null || otherB == null || b.equals(otherB)) + && c.equals(otherC) && this.d.equals(d) && this.e.equals(e) + && (f == null || otherF == null || f.equals(otherF)); } public boolean matches(Byte c, Byte d, Byte e) { diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/SmartMeterChannelTypeProvider.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/SmartMeterChannelTypeProvider.java index 0ce8d4667ba..7ec6381dd02 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/SmartMeterChannelTypeProvider.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/SmartMeterChannelTypeProvider.java @@ -21,7 +21,7 @@ import java.util.concurrent.ConcurrentHashMap; import javax.measure.Quantity; import javax.measure.Unit; -import org.eclipse.jdt.annotation.NonNull; +import org.eclipse.jdt.annotation.NonNullByDefault; import org.eclipse.jdt.annotation.Nullable; import org.openhab.binding.smartmeter.SmartMeterBindingConstants; import org.openhab.core.library.CoreItemFactory; @@ -44,6 +44,7 @@ import org.slf4j.LoggerFactory; * @author Matthias Steigenberger - Initial contribution * */ +@NonNullByDefault @Component(service = { ChannelTypeProvider.class, SmartMeterChannelTypeProvider.class }) public class SmartMeterChannelTypeProvider implements ChannelTypeProvider, MeterValueListener { @@ -68,14 +69,14 @@ public class SmartMeterChannelTypeProvider implements ChannelTypeProvider, Meter } @Override - public > void valueChanged(MeterValue value) { + public > void valueChanged(MeterValue value) { if (!obisChannelMap.containsKey(value.getObisCode())) { logger.debug("Creating ChannelType for OBIS {}", value.getObisCode()); obisChannelMap.put(value.getObisCode(), getChannelType(value.getUnit(), value.getObisCode())); } } - private ChannelType getChannelType(Unit unit, String obis) { + private ChannelType getChannelType(@Nullable Unit unit, String obis) { String obisChannelId = SmartMeterBindingConstants.getObisChannelId(obis); StateChannelTypeBuilder stateDescriptionBuilder; if (unit != null) { @@ -96,7 +97,7 @@ public class SmartMeterChannelTypeProvider implements ChannelTypeProvider, Meter } @Override - public > void valueRemoved(MeterValue value) { + public > void valueRemoved(MeterValue value) { obisChannelMap.remove(value.getObisCode()); } @@ -106,7 +107,7 @@ public class SmartMeterChannelTypeProvider implements ChannelTypeProvider, Meter * @param obis The obis code. * @return The {@link ChannelTypeUID} or null. */ - public ChannelTypeUID getChannelTypeIdForObis(String obis) { + public @Nullable ChannelTypeUID getChannelTypeIdForObis(String obis) { ChannelType channeltype = obisChannelMap.get(obis); return channeltype != null ? channeltype.getUID() : null; } diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/SmartMeterHandler.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/SmartMeterHandler.java index 22f5efc5aa9..d7aab5aafb7 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/SmartMeterHandler.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/SmartMeterHandler.java @@ -68,14 +68,13 @@ import io.reactivex.disposables.Disposable; public class SmartMeterHandler extends BaseThingHandler { private static final long DEFAULT_TIMEOUT = 30000; - private static final int DEFAULT_REFRESH_PERIOD = 30; private Logger logger = LoggerFactory.getLogger(SmartMeterHandler.class); private MeterDevice smlDevice; private Disposable valueReader; private Conformity conformity; private MeterValueListener valueChangeListener; private SmartMeterChannelTypeProvider channelTypeProvider; - private @NonNull Supplier serialPortManagerSupplier; + private Supplier serialPortManagerSupplier; public SmartMeterHandler(Thing thing, SmartMeterChannelTypeProvider channelProvider, Supplier serialPortManagerSupplier) { @@ -99,11 +98,10 @@ public class SmartMeterHandler extends BaseThingHandler { updateStatus(ThingStatus.OFFLINE, ThingStatusDetail.CONFIGURATION_ERROR, "Parameter 'port' is mandatory and must be configured"); } else { - byte[] pullSequence = config.initMessage == null ? null - : HexUtils.hexToBytes(config.initMessage.replaceAll("\\s+", "")); - int baudrate = config.baudrate == null ? Baudrate.AUTO.getBaudrate() - : Baudrate.fromString(config.baudrate).getBaudrate(); - this.conformity = config.conformity == null ? Conformity.NONE : Conformity.valueOf(config.conformity); + String initMessage = config.initMessage; + byte[] pullSequence = initMessage == null ? null : HexUtils.hexToBytes(initMessage.replaceAll("\\s+", "")); + int baudrate = Baudrate.fromString(config.baudrate).getBaudrate(); + this.conformity = Conformity.valueOf(config.conformity); this.smlDevice = MeterDeviceFactory.getDevice(serialPortManagerSupplier, config.mode, this.thing.getUID().getAsString(), port, pullSequence, baudrate, config.baudrateChangeDelay); updateStatus(ThingStatus.UNKNOWN, ThingStatusDetail.HANDLER_CONFIGURATION_PENDING, @@ -158,53 +156,58 @@ public class SmartMeterHandler extends BaseThingHandler { String obisChannelString = SmartMeterBindingConstants.getObisChannelId(obis); Channel channel = thing.getChannel(obisChannelString); + ChannelTypeUID channelTypeId = channelTypeProvider.getChannelTypeIdForObis(obis); + if (channelTypeId == null) { + logger.warn("No ChannelTypeId found for OBIS {}", obis); + return; + } ChannelType channelType = channelTypeProvider.getChannelType(channelTypeId, null); - if (channelType != null) { - String itemType = channelType.getItemType(); - - State state = getStateForObisValue(value, channel); - if (channel == null) { - logger.debug("Adding channel: {} with item type: {}", obisChannelString, itemType); - - // channel has not been created yet - ChannelBuilder channelBuilder = ChannelBuilder - .create(new ChannelUID(thing.getUID(), obisChannelString), itemType) - .withType(channelTypeId); - - Configuration configuration = new Configuration(); - configuration.put(SmartMeterBindingConstants.CONFIGURATION_CONVERSION, 1); - channelBuilder.withConfiguration(configuration); - channelBuilder.withLabel(obis); - Map channelProps = new HashMap<>(); - channelProps.put(SmartMeterBindingConstants.CHANNEL_PROPERTY_OBIS, obis); - channelBuilder.withProperties(channelProps); - channelBuilder.withDescription( - MessageFormat.format("Value for OBIS code: {0} with Unit: {1}", obis, value.getUnit())); - channel = channelBuilder.build(); - ChannelUID channelId = channel.getUID(); - - // add all valid channels to the thing builder - List channels = new ArrayList<>(getThing().getChannels()); - if (channels.stream().filter((element) -> element.getUID().equals(channelId)).count() == 0) { - channels.add(channel); - thingBuilder.withChannels(channels); - updateThing(thingBuilder.build()); - } - } - - if (!channel.getProperties().containsKey(SmartMeterBindingConstants.CHANNEL_PROPERTY_OBIS)) { - addObisPropertyToChannel(obis, channel); - } - if (state != null) { - updateState(channel.getUID(), state); - } - - updateStatus(ThingStatus.ONLINE, ThingStatusDetail.NONE); - } else { + if (channelType == null) { logger.warn("No ChannelType found for OBIS {}", obis); + return; } + String itemType = channelType.getItemType(); + + State state = getStateForObisValue(value, channel); + if (channel == null) { + logger.debug("Adding channel: {} with item type: {}", obisChannelString, itemType); + + // channel has not been created yet + ChannelBuilder channelBuilder = ChannelBuilder + .create(new ChannelUID(thing.getUID(), obisChannelString), itemType) + .withType(channelTypeId); + + Configuration configuration = new Configuration(); + configuration.put(SmartMeterBindingConstants.CONFIGURATION_CONVERSION, 1); + channelBuilder.withConfiguration(configuration); + channelBuilder.withLabel(obis); + Map channelProps = new HashMap<>(); + channelProps.put(SmartMeterBindingConstants.CHANNEL_PROPERTY_OBIS, obis); + channelBuilder.withProperties(channelProps); + channelBuilder.withDescription( + MessageFormat.format("Value for OBIS code: {0} with Unit: {1}", obis, value.getUnit())); + channel = channelBuilder.build(); + ChannelUID channelId = channel.getUID(); + + // add all valid channels to the thing builder + List channels = new ArrayList<>(getThing().getChannels()); + if (channels.stream().filter((element) -> element.getUID().equals(channelId)).count() == 0) { + channels.add(channel); + thingBuilder.withChannels(channels); + updateThing(thingBuilder.build()); + } + } + + if (!channel.getProperties().containsKey(SmartMeterBindingConstants.CHANNEL_PROPERTY_OBIS)) { + addObisPropertyToChannel(obis, channel); + } + if (state != null) { + updateState(channel.getUID(), state); + } + + updateStatus(ThingStatus.ONLINE, ThingStatusDetail.NONE); } private void addObisPropertyToChannel(String obis, Channel channel) { @@ -238,8 +241,7 @@ public class SmartMeterHandler extends BaseThingHandler { this.smlDevice.addValueChangeListener(valueChangeListener); SmartMeterConfiguration config = getConfigAs(SmartMeterConfiguration.class); - int delay = config.refresh != null ? config.refresh : DEFAULT_REFRESH_PERIOD; - valueReader = this.smlDevice.readValues(DEFAULT_TIMEOUT, this.scheduler, Duration.ofSeconds(delay)); + valueReader = this.smlDevice.readValues(DEFAULT_TIMEOUT, this.scheduler, Duration.ofSeconds(config.refresh)); } private void updateOBISChannel(ChannelUID channelId) { diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/conformity/Conformity.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/conformity/Conformity.java index 2ebf6b4e4a3..f707ae7baed 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/conformity/Conformity.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/conformity/Conformity.java @@ -28,7 +28,6 @@ import org.openhab.core.library.unit.Units; import org.openhab.core.thing.Channel; import org.openhab.core.thing.Thing; import org.openhab.core.types.State; -import org.slf4j.Logger; import org.slf4j.LoggerFactory; /** @@ -89,7 +88,8 @@ public enum Conformity { } } } catch (Exception e) { - logger.warn("Failed to check negate status for obis {}", obis, e); + LoggerFactory.getLogger(Conformity.class) + .warn("Failed to check negate status for obis {}", obis, e); } } } @@ -99,8 +99,6 @@ public enum Conformity { } }; - private static final Logger logger = LoggerFactory.getLogger(Conformity.class); - /** * Applies the overwritten negation setting for the channel. * diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/conformity/negate/NegateHandler.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/conformity/negate/NegateHandler.java index 64393645f1b..a96fd1064a6 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/conformity/negate/NegateHandler.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/conformity/negate/NegateHandler.java @@ -17,7 +17,6 @@ import java.util.function.Function; import org.eclipse.jdt.annotation.NonNullByDefault; import org.eclipse.jdt.annotation.Nullable; import org.openhab.binding.smartmeter.internal.MeterValue; -import org.slf4j.Logger; import org.slf4j.LoggerFactory; /** @@ -28,7 +27,6 @@ import org.slf4j.LoggerFactory; */ @NonNullByDefault public class NegateHandler { - private static final Logger LOGGER = LoggerFactory.getLogger(NegateHandler.class); /** * Gets whether negation should be applied for the given negateProperty and the {@link MeterValue} @@ -71,7 +69,8 @@ public class NegateHandler { try { longValue = (long) Double.parseDouble(value); } catch (NumberFormatException e) { - LOGGER.warn("Failed to parse value: {} when determining isNegateSet, assuming false", value); + LoggerFactory.getLogger(NegateHandler.class) + .warn("Failed to parse value: {} when determining isNegateSet, assuming false", value); return false; } return (longValue & (1L << negatePosition)) != 0; diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/Iec62056_21MeterReader.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/MeterReader.java similarity index 72% rename from bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/Iec62056_21MeterReader.java rename to bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/MeterReader.java index a49aa6fdb58..38520b79e04 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/Iec62056_21MeterReader.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/MeterReader.java @@ -16,7 +16,6 @@ import java.util.function.Supplier; import javax.measure.Quantity; -import org.eclipse.jdt.annotation.NonNull; import org.eclipse.jdt.annotation.NonNullByDefault; import org.eclipse.jdt.annotation.Nullable; import org.openhab.binding.smartmeter.connectors.IMeterReaderConnector; @@ -34,11 +33,10 @@ import org.openmuc.j62056.DataSet; * */ @NonNullByDefault -public class Iec62056_21MeterReader extends MeterDevice { +public class MeterReader extends MeterDevice { - public Iec62056_21MeterReader(Supplier serialPortManagerSupplier, String deviceId, - String serialPort, byte @Nullable [] initMessage, int baudrate, int baudrateChangeDelay, - ProtocolMode protocolMode) { + public MeterReader(Supplier serialPortManagerSupplier, String deviceId, String serialPort, + byte @Nullable [] initMessage, int baudrate, int baudrateChangeDelay, ProtocolMode protocolMode) { super(serialPortManagerSupplier, deviceId, serialPort, initMessage, baudrate, baudrateChangeDelay, protocolMode); } @@ -46,17 +44,15 @@ public class Iec62056_21MeterReader extends MeterDevice { @Override protected IMeterReaderConnector createConnector(Supplier serialPortManagerSupplier, String serialPort, int baudrate, int baudrateChangeDelay, ProtocolMode protocolMode) { - return new Iec62056_21SerialConnector(serialPortManagerSupplier, serialPort, baudrate, baudrateChangeDelay, - protocolMode); + return new SerialConnector(serialPortManagerSupplier, serialPort, baudrate, baudrateChangeDelay, protocolMode); } @Override - protected > void populateValueCache(DataMessage smlFile) { + protected > void populateValueCache(DataMessage smlFile) { for (DataSet dataSet : smlFile.getDataSets()) { String address = dataSet.getAddress(); if (address != null && !address.isEmpty()) { - addObisCache(new MeterValue(address, dataSet.getValue(), - Iec62056_21UnitConversion.getUnit(dataSet.getUnit()))); + addObisCache(new MeterValue(address, dataSet.getValue(), UnitConversion.getUnit(dataSet.getUnit()))); } } } diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/Iec62056_21SerialConnector.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/SerialConnector.java similarity index 89% rename from bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/Iec62056_21SerialConnector.java rename to bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/SerialConnector.java index 654a2e83090..3ec4131c0f5 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/Iec62056_21SerialConnector.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/SerialConnector.java @@ -40,17 +40,17 @@ import io.reactivex.FlowableEmitter; * */ @NonNullByDefault -public class Iec62056_21SerialConnector extends ConnectorBase { +public class SerialConnector extends ConnectorBase { - private final Logger logger = LoggerFactory.getLogger(Iec62056_21SerialConnector.class); + private final Logger logger = LoggerFactory.getLogger(SerialConnector.class); private int baudrate; private int baudrateChangeDelay; private ProtocolMode protocolMode; @Nullable private Iec21Port iec21Port; - public Iec62056_21SerialConnector(Supplier serialPortManagerSupplier, String portName, - int baudrate, int baudrateChangeDelay, ProtocolMode protocolMode) { + public SerialConnector(Supplier serialPortManagerSupplier, String portName, int baudrate, + int baudrateChangeDelay, ProtocolMode protocolMode) { super(portName); this.baudrate = baudrate; this.baudrateChangeDelay = baudrateChangeDelay; @@ -78,6 +78,7 @@ public class Iec62056_21SerialConnector extends ConnectorBase { @Override protected DataMessage readNext(byte @Nullable [] initMessage) throws IOException { + Iec21Port iec21Port = this.iec21Port; if (iec21Port != null) { DataMessage dataMessage = iec21Port.read(); logger.debug("Datamessage read: {}", dataMessage); @@ -94,6 +95,7 @@ public class Iec62056_21SerialConnector extends ConnectorBase { super.emitValues(initMessage, emitter); break; case D: + Iec21Port iec21Port = this.iec21Port; if (iec21Port != null) { iec21Port.listen(new ModeDListener() { @@ -108,6 +110,7 @@ public class Iec62056_21SerialConnector extends ConnectorBase { logger.warn("Exception while listening for mode D data message", e); } }); + this.iec21Port = iec21Port; } break; case SML: @@ -128,6 +131,7 @@ public class Iec62056_21SerialConnector extends ConnectorBase { @Override public void closeConnection() { + Iec21Port iec21Port = this.iec21Port; if (iec21Port != null) { iec21Port.close(); } diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/Iec62056_21UnitConversion.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/UnitConversion.java similarity index 82% rename from bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/Iec62056_21UnitConversion.java rename to bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/UnitConversion.java index 059f9ef52eb..a43cfe04621 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/Iec62056_21UnitConversion.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/iec62056/UnitConversion.java @@ -18,7 +18,6 @@ import javax.measure.Unit; import org.eclipse.jdt.annotation.NonNullByDefault; import org.eclipse.jdt.annotation.Nullable; import org.openhab.core.types.util.UnitUtils; -import org.slf4j.Logger; import org.slf4j.LoggerFactory; /** @@ -28,9 +27,7 @@ import org.slf4j.LoggerFactory; * */ @NonNullByDefault -public class Iec62056_21UnitConversion { - - private static final Logger logger = LoggerFactory.getLogger(Iec62056_21UnitConversion.class); +public class UnitConversion { @SuppressWarnings("unchecked") public static @Nullable > Unit getUnit(String unit) { @@ -38,7 +35,7 @@ public class Iec62056_21UnitConversion { try { return (Unit) UnitUtils.parseUnit(" " + unit); } catch (Exception e) { - logger.warn("Failed to parse unit {}: {}", unit, e.getMessage()); + LoggerFactory.getLogger(UnitConversion.class).warn("Failed to parse unit {}: {}", unit, e.getMessage()); return null; } } diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/sml/SmlFileDebugOutput.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/sml/SmlFileDebugOutput.java index 480256675eb..ae33730db29 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/sml/SmlFileDebugOutput.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/sml/SmlFileDebugOutput.java @@ -105,48 +105,48 @@ public class SmlFileDebugOutput { private static void parseGetListResponse(SmlMessage smlMessage, Consumer consumer) { consumer.accept("Got GetListResponse"); - SmlGetListRes sml_listRes = (SmlGetListRes) smlMessage.getMessageBody().getChoice(); + SmlGetListRes smlListRes = (SmlGetListRes) smlMessage.getMessageBody().getChoice(); // consumer.accept(sml_listRes.toString()); - consumer.accept(sml_listRes.toStringIndent(" ")); + consumer.accept(smlListRes.toStringIndent(" ")); } private static void parseAttentionResponse(SmlMessage smlMessage, Consumer consumer) { consumer.accept("Got AttentionResponse"); - SmlAttentionRes sml_attentionRes = (SmlAttentionRes) smlMessage.getMessageBody().getChoice(); - consumer.accept(sml_attentionRes.toString()); + SmlAttentionRes smlAttentionRes = (SmlAttentionRes) smlMessage.getMessageBody().getChoice(); + consumer.accept(smlAttentionRes.toString()); } private static void parseGetProcParameterResponse(SmlMessage smlMessage, Consumer consumer) { consumer.accept("Got GetProcParameterResponse"); - SmlGetProcParameterRes sml_getProcParameterRes = (SmlGetProcParameterRes) smlMessage.getMessageBody() + SmlGetProcParameterRes smlGetProcParameterRes = (SmlGetProcParameterRes) smlMessage.getMessageBody() .getChoice(); - consumer.accept(sml_getProcParameterRes.toString()); + consumer.accept(smlGetProcParameterRes.toString()); } private static void parseGetProfileListResponse(SmlMessage smlMessage, Consumer consumer) { consumer.accept("Got GetProfileListResponse"); - SmlGetProfileListRes sml_getProfileListRes = (SmlGetProfileListRes) smlMessage.getMessageBody().getChoice(); - consumer.accept(sml_getProfileListRes.toString()); + SmlGetProfileListRes smlGetProfileListRes = (SmlGetProfileListRes) smlMessage.getMessageBody().getChoice(); + consumer.accept(smlGetProfileListRes.toString()); } private static void parseOpenResponse(SmlMessage smlMessage, Consumer consumer) { consumer.accept("Got OpenResponse"); - SmlPublicOpenRes sml_PublicOpenRes = (SmlPublicOpenRes) smlMessage.getMessageBody().getChoice(); - consumer.accept(sml_PublicOpenRes.toString()); + SmlPublicOpenRes smlPublicOpenRes = (SmlPublicOpenRes) smlMessage.getMessageBody().getChoice(); + consumer.accept(smlPublicOpenRes.toString()); } private static void parseCloseResponse(SmlMessage smlMessage, Consumer consumer) { consumer.accept("Got CloseResponse"); - SmlPublicCloseRes sml_PublicCloseRes = (SmlPublicCloseRes) smlMessage.getMessageBody().getChoice(); - consumer.accept(sml_PublicCloseRes.toString()); + SmlPublicCloseRes smlPublicCloseRes = (SmlPublicCloseRes) smlMessage.getMessageBody().getChoice(); + consumer.accept(smlPublicCloseRes.toString()); } private static void parseGetProfilePackResponse(SmlMessage smlMessage, Consumer consumer) { consumer.accept("Got GetProfilePackResponse"); - SmlGetProfilePackRes sml_getProfilePackRes = (SmlGetProfilePackRes) smlMessage.getMessageBody().getChoice(); - consumer.accept(sml_getProfilePackRes.toString()); + SmlGetProfilePackRes smlGetProfilePackRes = (SmlGetProfilePackRes) smlMessage.getMessageBody().getChoice(); + consumer.accept(smlGetProfilePackRes.toString()); } // ========================= Requests ================================= diff --git a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/sml/SmlSerialConnector.java b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/sml/SmlSerialConnector.java index 8e1959fadb3..c1004f25639 100644 --- a/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/sml/SmlSerialConnector.java +++ b/bundles/org.openhab.binding.smartmeter/src/main/java/org/openhab/binding/smartmeter/internal/sml/SmlSerialConnector.java @@ -81,6 +81,7 @@ public final class SmlSerialConnector extends ConnectorBase { protected SmlFile readNext(byte @Nullable [] initMessage) throws IOException { if (initMessage != null) { logger.debug("Writing init message: {}", HexUtils.bytesToHex(initMessage, " ")); + DataOutputStream os = this.os; if (os != null) { os.write(initMessage); os.flush(); @@ -89,6 +90,7 @@ public final class SmlSerialConnector extends ConnectorBase { // read out the whole buffer. We are only interested in the most recent SML file. Stack smlFiles = new Stack<>(); + DataInputStream is = this.is; do { logger.trace("Reading {}. SML message", smlFiles.size() + 1); smlFiles.push(TRANSPORT.getSMLFile(is)); @@ -137,12 +139,10 @@ public final class SmlSerialConnector extends ConnectorBase { } } - /** - * {@inheritDoc} - */ @Override public void closeConnection() { try { + DataInputStream is = this.is; if (is != null) { is.close(); is = null; @@ -151,6 +151,7 @@ public final class SmlSerialConnector extends ConnectorBase { logger.error("Failed to close serial input stream", e); } try { + DataOutputStream os = this.os; if (os != null) { os.close(); os = null; diff --git a/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/MockMeterReaderConnector.java b/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/MockMeterReaderConnector.java index 25b41dd91f0..81f601902bc 100644 --- a/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/MockMeterReaderConnector.java +++ b/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/MockMeterReaderConnector.java @@ -15,6 +15,8 @@ package org.openhab.binding.smartmeter; import java.io.IOException; import java.util.function.Supplier; +import org.eclipse.jdt.annotation.NonNullByDefault; +import org.eclipse.jdt.annotation.Nullable; import org.openhab.binding.smartmeter.connectors.ConnectorBase; /** @@ -22,6 +24,7 @@ import org.openhab.binding.smartmeter.connectors.ConnectorBase; * @author Matthias Steigenberger - Initial contribution * */ +@NonNullByDefault public class MockMeterReaderConnector extends ConnectorBase { private boolean applyRetry; @@ -42,12 +45,12 @@ public class MockMeterReaderConnector extends ConnectorBase { } @Override - protected Object readNext(byte[] initMessage) throws IOException { + protected Object readNext(byte @Nullable [] initMessage) throws IOException { try { return readNextSupplier.get(); } catch (RuntimeException e) { - if (e.getCause() instanceof IOException) { - throw (IOException) e.getCause(); + if (e.getCause() instanceof IOException cause) { + throw cause; } throw e; } diff --git a/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/TestMeterReading.java b/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/TestMeterReading.java index 5f3acee9588..54ad89ffc0b 100644 --- a/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/TestMeterReading.java +++ b/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/TestMeterReading.java @@ -23,7 +23,7 @@ import java.util.function.Supplier; import javax.measure.Quantity; -import org.eclipse.jdt.annotation.NonNull; +import org.eclipse.jdt.annotation.NonNullByDefault; import org.junit.jupiter.api.Test; import org.mockito.ArgumentMatchers; import org.mockito.Mockito; @@ -44,6 +44,7 @@ import io.reactivex.plugins.RxJavaPlugins; * @author Matthias Steigenberger - Initial contribution * */ +@NonNullByDefault public class TestMeterReading { @Test @@ -118,6 +119,7 @@ public class TestMeterReading { throw new RuntimeException(new IOException("fucked up")); })); MeterDevice meter = getMeterDevice(connector); + @SuppressWarnings("unchecked") Consumer errorHandler = mock(Consumer.class); RxJavaPlugins.setErrorHandler(errorHandler); MeterValueListener changeListener = Mockito.mock(MeterValueListener.class); @@ -139,14 +141,15 @@ public class TestMeterReading { return new MeterDevice<>(() -> mock(SerialPortManager.class), "id", "port", null, 9600, 0, ProtocolMode.SML) { @Override - protected @NonNull IMeterReaderConnector createConnector( - @NonNull Supplier<@NonNull SerialPortManager> serialPortManagerSupplier, @NonNull String serialPort, - int baudrate, int baudrateChangeDelay, @NonNull ProtocolMode protocolMode) { + protected IMeterReaderConnector createConnector( + Supplier serialPortManagerSupplier, String serialPort, int baudrate, + int baudrateChangeDelay, ProtocolMode protocolMode) { return connector; } + @SuppressWarnings({ "rawtypes", "unchecked" }) @Override - protected > void populateValueCache(Object smlFile) { + protected > void populateValueCache(Object smlFile) { addObisCache(new MeterValue("123", "333", null)); } }; diff --git a/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/TestNegateBit.java b/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/TestNegateBit.java index 4b6de5643c5..dc919d10738 100644 --- a/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/TestNegateBit.java +++ b/bundles/org.openhab.binding.smartmeter/src/test/java/org/openhab/binding/smartmeter/TestNegateBit.java @@ -14,6 +14,7 @@ package org.openhab.binding.smartmeter; import static org.junit.jupiter.api.Assertions.*; +import org.eclipse.jdt.annotation.NonNullByDefault; import org.junit.jupiter.api.Test; import org.openhab.binding.smartmeter.internal.MeterValue; import org.openhab.binding.smartmeter.internal.conformity.negate.NegateBitModel; @@ -25,6 +26,7 @@ import org.openhab.binding.smartmeter.internal.conformity.negate.NegateHandler; * @author Matthias Steigenberger - Initial contribution * */ +@NonNullByDefault public class TestNegateBit { @Test