2 * Copyright (c) 2010-2023 Contributors to the openHAB project
4 * See the NOTICE file(s) distributed with this work for additional
7 * This program and the accompanying materials are made available under the
8 * terms of the Eclipse Public License 2.0 which is available at
9 * http://www.eclipse.org/legal/epl-2.0
11 * SPDX-License-Identifier: EPL-2.0
13 package org.openhab.binding.modbus.tests;
15 import static org.hamcrest.CoreMatchers.*;
16 import static org.hamcrest.MatcherAssert.assertThat;
17 import static org.junit.jupiter.api.Assertions.*;
19 import java.util.Objects;
21 import org.junit.jupiter.api.Test;
22 import org.mockito.InOrder;
23 import org.mockito.Mockito;
24 import org.openhab.binding.modbus.handler.EndpointNotInitializedException;
25 import org.openhab.binding.modbus.internal.ModbusBindingConstantsInternal;
26 import org.openhab.binding.modbus.internal.handler.ModbusTcpThingHandler;
27 import org.openhab.core.config.core.Configuration;
28 import org.openhab.core.io.transport.modbus.endpoint.EndpointPoolConfiguration;
29 import org.openhab.core.io.transport.modbus.endpoint.ModbusSlaveEndpoint;
30 import org.openhab.core.io.transport.modbus.endpoint.ModbusTCPSlaveEndpoint;
31 import org.openhab.core.thing.Bridge;
32 import org.openhab.core.thing.ThingStatus;
33 import org.openhab.core.thing.ThingStatusDetail;
34 import org.openhab.core.thing.ThingUID;
35 import org.openhab.core.thing.binding.builder.BridgeBuilder;
38 * @author Sami Salonen - Initial contribution
40 public class ModbusTcpThingHandlerTest extends AbstractModbusOSGiTest {
42 private static BridgeBuilder createTcpThingBuilder(String id) {
43 return BridgeBuilder.create(ModbusBindingConstantsInternal.THING_TYPE_MODBUS_TCP,
44 new ThingUID(ModbusBindingConstantsInternal.THING_TYPE_MODBUS_TCP, id));
48 public void testInitializeAndSlaveEndpoint() throws EndpointNotInitializedException {
49 // Using mocked modbus manager
50 Configuration thingConfig = new Configuration();
51 thingConfig.put("host", "thisishost");
52 thingConfig.put("port", 44);
53 thingConfig.put("id", 9);
54 thingConfig.put("timeBetweenTransactionsMillis", 1);
55 thingConfig.put("timeBetweenReconnectMillis", 2);
56 thingConfig.put("connectMaxTries", 3);
57 thingConfig.put("reconnectAfterMillis", 4);
58 thingConfig.put("connectTimeoutMillis", 5);
60 EndpointPoolConfiguration expectedPoolConfiguration = new EndpointPoolConfiguration();
61 expectedPoolConfiguration.setConnectMaxTries(3);
62 expectedPoolConfiguration.setConnectTimeoutMillis(5);
63 expectedPoolConfiguration.setInterConnectDelayMillis(2);
64 expectedPoolConfiguration.setInterTransactionDelayMillis(1);
65 expectedPoolConfiguration.setReconnectAfterMillis(4);
67 Bridge thing = createTcpThingBuilder("tcpendpoint").withConfiguration(thingConfig).build();
69 assertThat(thing.getStatus(), is(equalTo(ThingStatus.ONLINE)));
71 ModbusTcpThingHandler thingHandler = (ModbusTcpThingHandler) thing.getHandler();
72 assertNotNull(thingHandler);
73 ModbusSlaveEndpoint slaveEndpoint = thingHandler.getEndpoint();
74 assertThat(slaveEndpoint, is(equalTo(new ModbusTCPSlaveEndpoint("thisishost", 44, false))));
75 assertThat(thingHandler.getSlaveId(), is(9));
77 InOrder orderedVerify = Mockito.inOrder(mockedModbusManager);
78 ModbusSlaveEndpoint endpoint = thingHandler.getEndpoint();
79 Objects.requireNonNull(endpoint);
80 orderedVerify.verify(mockedModbusManager).newModbusCommunicationInterface(endpoint, expectedPoolConfiguration);
84 public void testTwoDifferentEndpointWithDifferentParameters() {
85 // Real implementation needed to validate this behaviour
86 swapModbusManagerToReal();
89 Configuration thingConfig = new Configuration();
90 thingConfig.put("host", "thisishost");
91 thingConfig.put("port", 44);
92 thingConfig.put("connectMaxTries", 1);
93 thingConfig.put("timeBetweenTransactionsMillis", 1);
95 final Bridge thing = createTcpThingBuilder("tcpendpoint").withConfiguration(thingConfig).build();
97 assertThat(thing.getStatus(), is(equalTo(ThingStatus.ONLINE)));
99 ModbusTcpThingHandler thingHandler = (ModbusTcpThingHandler) thing.getHandler();
100 assertNotNull(thingHandler);
102 EndpointPoolConfiguration expectedPoolConfiguration = new EndpointPoolConfiguration();
103 expectedPoolConfiguration.setConnectMaxTries(1);
104 expectedPoolConfiguration.setInterTransactionDelayMillis(1);
107 expectedPoolConfiguration.setConnectTimeoutMillis(10_000);
108 expectedPoolConfiguration.setInterConnectDelayMillis(0);
109 expectedPoolConfiguration.setReconnectAfterMillis(0);
111 assertEquals(expectedPoolConfiguration, realModbusManager
112 .getEndpointPoolConfiguration(new ModbusTCPSlaveEndpoint("thisishost", 44, false)));
115 Configuration thingConfig = new Configuration();
116 thingConfig.put("host", "thisishost");
117 thingConfig.put("port", 45);
118 thingConfig.put("connectMaxTries", 1);
119 thingConfig.put("timeBetweenTransactionsMillis", 100);
121 final Bridge thing = createTcpThingBuilder("tcpendpoint2").withConfiguration(thingConfig).build();
123 // Different endpoint (port 45), so should be OK even though timeBetweenTransactionsMillis is different
124 assertThat(thing.getStatus(), is(equalTo(ThingStatus.ONLINE)));
126 ModbusTcpThingHandler thingHandler = (ModbusTcpThingHandler) thing.getHandler();
127 assertNotNull(thingHandler);
132 public void testTwoIdenticalEndpointWithDifferentParameters() {
133 // Real implementation needed to validate this behaviour
134 swapModbusManagerToReal();
137 Configuration thingConfig = new Configuration();
138 thingConfig.put("host", "thisishost");
139 thingConfig.put("port", 44);
140 thingConfig.put("connectMaxTries", 1);
141 thingConfig.put("timeBetweenTransactionsMillis", 1);
143 final Bridge thing = createTcpThingBuilder("tcpendpoint").withConfiguration(thingConfig).build();
145 assertThat(thing.getStatus(), is(equalTo(ThingStatus.ONLINE)));
147 ModbusTcpThingHandler thingHandler = (ModbusTcpThingHandler) thing.getHandler();
148 assertNotNull(thingHandler);
152 Configuration thingConfig = new Configuration();
153 thingConfig.put("host", "thisishost");
154 thingConfig.put("port", 44);
155 thingConfig.put("connectMaxTries", 1);
156 thingConfig.put("timeBetweenTransactionsMillis", 100);
158 final Bridge thing = createTcpThingBuilder("tcpendpoint2").withConfiguration(thingConfig).build();
160 assertThat(thing.getStatus(), is(equalTo(ThingStatus.OFFLINE)));
161 assertThat(thing.getStatusInfo().getStatusDetail(), is(equalTo(ThingStatusDetail.CONFIGURATION_ERROR)));
165 // Ensure the right EndpointPoolConfiguration is still in place
167 EndpointPoolConfiguration expectedPoolConfiguration = new EndpointPoolConfiguration();
168 expectedPoolConfiguration.setConnectMaxTries(1);
169 expectedPoolConfiguration.setInterTransactionDelayMillis(1); // Note: not 100
172 expectedPoolConfiguration.setConnectTimeoutMillis(10_000);
173 expectedPoolConfiguration.setInterConnectDelayMillis(0);
174 expectedPoolConfiguration.setReconnectAfterMillis(0);
176 assertEquals(expectedPoolConfiguration, realModbusManager
177 .getEndpointPoolConfiguration(new ModbusTCPSlaveEndpoint("thisishost", 44, false)));
182 public void testTwoIdenticalEndpointWithSameParameters() {
183 // Real implementation needed to validate this behaviour
184 swapModbusManagerToReal();
187 Configuration thingConfig = new Configuration();
188 thingConfig.put("host", "thisishost");
189 thingConfig.put("port", 44);
190 thingConfig.put("connectMaxTries", 1);
191 thingConfig.put("timeBetweenTransactionsMillis", 1);
193 final Bridge thing = createTcpThingBuilder("tcpendpoint").withConfiguration(thingConfig).build();
195 assertThat(thing.getStatus(), is(equalTo(ThingStatus.ONLINE)));
197 ModbusTcpThingHandler thingHandler = (ModbusTcpThingHandler) thing.getHandler();
198 assertNotNull(thingHandler);
201 Configuration thingConfig = new Configuration();
202 thingConfig.put("host", "thisishost");
203 thingConfig.put("port", 44);
204 thingConfig.put("connectMaxTries", 1);
205 thingConfig.put("timeBetweenTransactionsMillis", 1);
206 thingConfig.put("connectTimeoutMillis", 10000); // default
208 final Bridge thing = createTcpThingBuilder("tcpendpoint2").withConfiguration(thingConfig).build();
210 // Same endpoint and same parameters -> should not affect this thing
211 assertThat(thing.getStatus(), is(equalTo(ThingStatus.ONLINE)));