diff --git a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/AbstractConnectionState.java b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/AbstractConnectionState.java index 78c1e0cc2ba00..e2151f1a5f7bc 100644 --- a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/AbstractConnectionState.java +++ b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/AbstractConnectionState.java @@ -17,6 +17,7 @@ import java.util.concurrent.ScheduledExecutorService; import org.eclipse.jdt.annotation.NonNullByDefault; +import org.eclipse.jdt.annotation.Nullable; import org.openhab.binding.lcn.internal.common.LcnAddr; import org.openhab.binding.lcn.internal.common.LcnDefs; @@ -84,6 +85,23 @@ protected void parseLcnBusDiconnectMessage(String pck) { } } + /** + * Invoked by any state, if the connection fails. + * + * @param e the cause + */ + public void handleConnectionFailed(@Nullable Throwable e) { + synchronized (context) { + if (e != null) { + String message = e.getMessage(); + connection.getCallback().onOffline(message != null ? message : ""); + } else { + connection.getCallback().onOffline(""); + } + context.setState(ConnectionStateGracePeriodBeforeReconnect::new); + } + } + /** * Closes the Connection SocketChannel. */ diff --git a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/AbstractConnectionStateSendCredentials.java b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/AbstractConnectionStateSendCredentials.java index ab91729bb000b..b0b7978249012 100644 --- a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/AbstractConnectionStateSendCredentials.java +++ b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/AbstractConnectionStateSendCredentials.java @@ -41,7 +41,7 @@ public void startWorking() { */ protected void startTimeoutTimer() { addTimer(getScheduler().schedule( - () -> context.handleConnectionFailed( + () -> handleConnectionFailed( new LcnException("Network timeout in state " + getClass().getSimpleName())), connection.getSettings().getTimeout(), TimeUnit.MILLISECONDS)); } diff --git a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateConnecting.java b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateConnecting.java index aee67ed1c3bd4..26b9c00c74519 100644 --- a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateConnecting.java +++ b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateConnecting.java @@ -86,7 +86,7 @@ private void handleConnectionFailure(@Nullable Throwable e) { message = e.getMessage(); } connection.getCallback().onOffline(Objects.requireNonNullElse(message, "")); - context.handleConnectionFailed(e); + handleConnectionFailed(e); } @Override diff --git a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateGracePeriodBeforeReconnect.java b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateGracePeriodBeforeReconnect.java index 3781a533774a5..34775b7cb5f7a 100644 --- a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateGracePeriodBeforeReconnect.java +++ b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateGracePeriodBeforeReconnect.java @@ -15,6 +15,7 @@ import java.util.concurrent.TimeUnit; import org.eclipse.jdt.annotation.NonNullByDefault; +import org.eclipse.jdt.annotation.Nullable; /** * This state is active when the connection failed. A grace period is enforced to prevent fast cycling through the @@ -42,4 +43,9 @@ public void startWorking() { public void onPckMessageReceived(String data) { // nothing } + + @Override + public void handleConnectionFailed(@Nullable Throwable e) { + // nothing + } } diff --git a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateMachine.java b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateMachine.java index cb75755433d95..5e97faf0cc731 100644 --- a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateMachine.java +++ b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateMachine.java @@ -46,7 +46,7 @@ protected ScheduledExecutorService getScheduler() { /** * Gets the PCHK Connection object. - * + * * @return the connection */ public Connection getConnection() { @@ -72,15 +72,10 @@ public void queue(LcnAddr addr, boolean wantsAck, byte[] data) { * * @param e the cause */ - public void handleConnectionFailed(@Nullable Throwable e) { - if (!(state instanceof ConnectionStateShutdown)) { - if (e != null) { - String message = e.getMessage(); - connection.getCallback().onOffline(message != null ? message : ""); - } else { - connection.getCallback().onOffline(""); - } - setState(ConnectionStateGracePeriodBeforeReconnect::new); + public synchronized void handleConnectionFailed(@Nullable Throwable e) { + AbstractConnectionState localState = state; + if (localState != null) { + localState.handleConnectionFailed(e); } } diff --git a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateShutdown.java b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateShutdown.java index 7179b07bff15d..37048176e6663 100644 --- a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateShutdown.java +++ b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateShutdown.java @@ -13,6 +13,7 @@ package org.openhab.binding.lcn.internal.connection; import org.eclipse.jdt.annotation.NonNullByDefault; +import org.eclipse.jdt.annotation.Nullable; import org.openhab.binding.lcn.internal.common.LcnAddr; /** @@ -42,4 +43,9 @@ public void queue(LcnAddr addr, boolean wantsAck, byte[] data) { public void onPckMessageReceived(String data) { // nothing } + + @Override + public void handleConnectionFailed(@Nullable Throwable e) { + // nothing + } } diff --git a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateWaitForLcnBusConnected.java b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateWaitForLcnBusConnected.java index 61ff6a93f7518..2eadfb1da1c07 100644 --- a/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateWaitForLcnBusConnected.java +++ b/bundles/org.openhab.binding.lcn/src/main/java/org/openhab/binding/lcn/internal/connection/ConnectionStateWaitForLcnBusConnected.java @@ -48,21 +48,28 @@ public void startWorking() { @Override public void onPckMessageReceived(String data) { + switch (data) { + case LcnDefs.LCNCONNSTATE_DISCONNECTED: + cancelLegacyTimer(); + connection.getCallback().onOffline("LCN bus not connected to LCN-PCHK/PKE"); + break; + case LcnDefs.LCNCONNSTATE_CONNECTED: + cancelLegacyTimer(); + connection.getCallback().onOnline(); + nextState(ConnectionStateSendDimMode::new); + break; + case LcnDefs.INSUFFICIENT_LICENSES: + cancelLegacyTimer(); + handleConnectionFailed( + new LcnException("LCN-PCHK/PKE has not enough licenses to handle this connection")); + break; + } + } + + private void cancelLegacyTimer() { ScheduledFuture localLegacyTimer = legacyTimer; - if (data.equals(LcnDefs.LCNCONNSTATE_DISCONNECTED)) { - if (localLegacyTimer != null) { - localLegacyTimer.cancel(true); - } - connection.getCallback().onOffline("LCN bus not connected to LCN-PCHK/PKE"); - } else if (data.equals(LcnDefs.LCNCONNSTATE_CONNECTED)) { - if (localLegacyTimer != null) { - localLegacyTimer.cancel(true); - } - connection.getCallback().onOnline(); - nextState(ConnectionStateSendDimMode::new); - } else if (data.equals(LcnDefs.INSUFFICIENT_LICENSES)) { - context.handleConnectionFailed( - new LcnException("LCN-PCHK/PKE has not enough licenses to handle this connection")); + if (localLegacyTimer != null) { + localLegacyTimer.cancel(true); } } }