2 * Copyright (c) 2010-2022 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.mqtt.generic.values;
15 import static org.hamcrest.CoreMatchers.is;
16 import static org.hamcrest.MatcherAssert.assertThat;
17 import static org.junit.jupiter.api.Assertions.*;
19 import java.math.BigDecimal;
21 import org.junit.jupiter.api.Test;
22 import org.openhab.binding.mqtt.generic.mapping.ColorMode;
23 import org.openhab.core.library.types.DecimalType;
24 import org.openhab.core.library.types.HSBType;
25 import org.openhab.core.library.types.IncreaseDecreaseType;
26 import org.openhab.core.library.types.OnOffType;
27 import org.openhab.core.library.types.OpenClosedType;
28 import org.openhab.core.library.types.PercentType;
29 import org.openhab.core.library.types.QuantityType;
30 import org.openhab.core.library.types.StringType;
31 import org.openhab.core.library.types.UpDownType;
32 import org.openhab.core.library.unit.MetricPrefix;
33 import org.openhab.core.library.unit.Units;
34 import org.openhab.core.types.Command;
35 import org.openhab.core.types.TypeParser;
38 * Test cases for the value classes. They should throw exceptions if the wrong command type is used
39 * for an update. The percent value class should raise an exception if the value is out of range.
41 * The on/off value class should accept a multitude of values including the custom defined ones.
43 * The string value class states are tested.
45 * @author David Graeff - Initial contribution
47 public class ValueTests {
48 Command p(Value v, String str) {
49 return TypeParser.parseCommand(v.getSupportedCommandTypes(), str);
53 public void illegalTextStateUpdate() {
54 TextValue v = new TextValue("one,two".split(","));
55 assertThrows(IllegalArgumentException.class, () -> v.update(p(v, "three")));
58 public void textStateUpdate() {
59 TextValue v = new TextValue("one,two".split(","));
60 v.update(p(v, "one"));
63 public void colorUpdate() {
64 ColorValue v = new ColorValue(ColorMode.RGB, "fancyON", "fancyOFF", 77);
65 v.update(p(v, "255, 255, 255"));
67 v.update(p(v, "OFF"));
68 assertThat(((HSBType) v.getChannelState()).getBrightness().intValue(), is(0));
70 assertThat(((HSBType) v.getChannelState()).getBrightness().intValue(), is(77));
73 assertThat(((HSBType) v.getChannelState()).getBrightness().intValue(), is(0));
75 assertThat(((HSBType) v.getChannelState()).getBrightness().intValue(), is(1));
79 public void illegalColorUpdate() {
80 ColorValue v = new ColorValue(ColorMode.RGB, null, null, 10);
81 assertThrows(IllegalArgumentException.class, () -> v.update(p(v, "255,255,abc")));
85 public void illegalNumberCommand() {
86 NumberValue v = new NumberValue(null, null, null, null);
87 assertThrows(IllegalArgumentException.class, () -> v.update(OnOffType.OFF));
91 public void illegalPercentCommand() {
92 PercentageValue v = new PercentageValue(null, null, null, null, null);
93 assertThrows(IllegalStateException.class, () -> v.update(new StringType("demo")));
97 public void illegalOnOffCommand() {
98 OnOffValue v = new OnOffValue(null, null);
99 assertThrows(IllegalArgumentException.class, () -> v.update(new DecimalType(101.0)));
103 public void illegalPercentUpdate() {
104 PercentageValue v = new PercentageValue(null, null, null, null, null);
105 assertThrows(IllegalArgumentException.class, () -> v.update(new DecimalType(101.0)));
109 public void onoffUpdate() {
110 OnOffValue v = new OnOffValue("fancyON", "fancyOff");
112 v.update(OnOffType.OFF);
113 assertThat(v.getMQTTpublishValue(null), is("fancyOff"));
114 assertThat(v.getChannelState(), is(OnOffType.OFF));
115 v.update(OnOffType.ON);
116 assertThat(v.getMQTTpublishValue(null), is("fancyON"));
117 assertThat(v.getChannelState(), is(OnOffType.ON));
119 // Test with string, representing the command
120 v.update(new StringType("OFF"));
121 assertThat(v.getMQTTpublishValue(null), is("fancyOff"));
122 assertThat(v.getChannelState(), is(OnOffType.OFF));
123 v.update(new StringType("ON"));
124 assertThat(v.getMQTTpublishValue(null), is("fancyON"));
125 assertThat(v.getChannelState(), is(OnOffType.ON));
127 // Test with custom string, setup in the constructor
128 v.update(new StringType("fancyOff"));
129 assertThat(v.getMQTTpublishValue(null), is("fancyOff"));
130 assertThat(v.getMQTTpublishValue("=%s"), is("=fancyOff"));
131 assertThat(v.getChannelState(), is(OnOffType.OFF));
132 v.update(new StringType("fancyON"));
133 assertThat(v.getMQTTpublishValue(null), is("fancyON"));
134 assertThat(v.getMQTTpublishValue("=%s"), is("=fancyON"));
135 assertThat(v.getChannelState(), is(OnOffType.ON));
139 public void openCloseUpdate() {
140 OpenCloseValue v = new OpenCloseValue("fancyON", "fancyOff");
142 v.update(OpenClosedType.CLOSED);
143 assertThat(v.getMQTTpublishValue(null), is("fancyOff"));
144 assertThat(v.getChannelState(), is(OpenClosedType.CLOSED));
145 v.update(OpenClosedType.OPEN);
146 assertThat(v.getMQTTpublishValue(null), is("fancyON"));
147 assertThat(v.getChannelState(), is(OpenClosedType.OPEN));
149 // Test with string, representing the command
150 v.update(new StringType("CLOSED"));
151 assertThat(v.getMQTTpublishValue(null), is("fancyOff"));
152 assertThat(v.getChannelState(), is(OpenClosedType.CLOSED));
153 v.update(new StringType("OPEN"));
154 assertThat(v.getMQTTpublishValue(null), is("fancyON"));
155 assertThat(v.getChannelState(), is(OpenClosedType.OPEN));
157 // Test with custom string, setup in the constructor
158 v.update(new StringType("fancyOff"));
159 assertThat(v.getMQTTpublishValue(null), is("fancyOff"));
160 assertThat(v.getChannelState(), is(OpenClosedType.CLOSED));
161 v.update(new StringType("fancyON"));
162 assertThat(v.getMQTTpublishValue(null), is("fancyON"));
163 assertThat(v.getChannelState(), is(OpenClosedType.OPEN));
167 public void numberUpdate() {
168 NumberValue v = new NumberValue(null, null, new BigDecimal(10), Units.WATT);
170 // Test with command with units
171 v.update(new QuantityType<>(20, Units.WATT));
172 assertThat(v.getMQTTpublishValue(null), is("20"));
173 assertThat(v.getChannelState(), is(new QuantityType<>(20, Units.WATT)));
174 v.update(new QuantityType<>(20, MetricPrefix.KILO(Units.WATT)));
175 assertThat(v.getMQTTpublishValue(null), is("20000"));
176 assertThat(v.getChannelState(), is(new QuantityType<>(20, MetricPrefix.KILO(Units.WATT))));
178 // Test with command without units
179 v.update(new QuantityType<>("20"));
180 assertThat(v.getMQTTpublishValue(null), is("20"));
181 assertThat(v.getChannelState(), is(new QuantityType<>(20, Units.WATT)));
185 public void numberPercentageUpdate() {
186 NumberValue v = new NumberValue(null, null, new BigDecimal(10), Units.PERCENT);
188 // Test with command with units
189 v.update(new QuantityType<>(20, Units.PERCENT));
190 assertThat(v.getMQTTpublishValue(null), is("20"));
191 assertThat(v.getChannelState(), is(new QuantityType<>(20, Units.PERCENT)));
193 // Test with command without units
194 v.update(new QuantityType<>("20"));
195 assertThat(v.getMQTTpublishValue(null), is("20"));
196 assertThat(v.getChannelState(), is(new QuantityType<>(20, Units.PERCENT)));
200 public void rollershutterUpdateWithStrings() {
201 RollershutterValue v = new RollershutterValue("fancyON", "fancyOff", "fancyStop");
203 v.update(UpDownType.UP);
204 assertThat(v.getMQTTpublishValue(null), is("fancyON"));
205 assertThat(v.getChannelState(), is(PercentType.ZERO));
206 v.update(UpDownType.DOWN);
207 assertThat(v.getMQTTpublishValue(null), is("fancyOff"));
208 assertThat(v.getChannelState(), is(PercentType.HUNDRED));
210 // Test with custom string
211 v.update(new StringType("fancyON"));
212 assertThat(v.getMQTTpublishValue(null), is("fancyON"));
213 assertThat(v.getChannelState(), is(PercentType.ZERO));
214 v.update(new StringType("fancyOff"));
215 assertThat(v.getMQTTpublishValue(null), is("fancyOff"));
216 assertThat(v.getChannelState(), is(PercentType.HUNDRED));
217 v.update(new PercentType(27));
218 assertThat(v.getMQTTpublishValue(null), is("27"));
219 assertThat(v.getChannelState(), is(new PercentType(27)));
223 public void rollershutterUpdateWithOutStrings() {
224 RollershutterValue v = new RollershutterValue(null, null, "fancyStop");
226 v.update(UpDownType.UP);
227 assertThat(v.getMQTTpublishValue(null), is("0"));
228 assertThat(v.getChannelState(), is(PercentType.ZERO));
229 v.update(UpDownType.DOWN);
230 assertThat(v.getMQTTpublishValue(null), is("100"));
231 assertThat(v.getChannelState(), is(PercentType.HUNDRED));
233 // Test with custom string
234 v.update(PercentType.ZERO);
235 assertThat(v.getMQTTpublishValue(null), is("0"));
236 assertThat(v.getChannelState(), is(PercentType.ZERO));
237 v.update(PercentType.HUNDRED);
238 assertThat(v.getMQTTpublishValue(null), is("100"));
239 assertThat(v.getChannelState(), is(PercentType.HUNDRED));
240 v.update(new PercentType(27));
241 assertThat(v.getMQTTpublishValue(null), is("27"));
242 assertThat(v.getChannelState(), is(new PercentType(27)));
246 public void percentCalc() {
247 PercentageValue v = new PercentageValue(new BigDecimal(10.0), new BigDecimal(110.0), new BigDecimal(1.0), null,
249 v.update(new DecimalType("110.0"));
250 assertThat((PercentType) v.getChannelState(), is(new PercentType(100)));
251 assertThat(v.getMQTTpublishValue(null), is("110"));
252 v.update(new DecimalType(10.0));
253 assertThat((PercentType) v.getChannelState(), is(new PercentType(0)));
254 assertThat(v.getMQTTpublishValue(null), is("10"));
256 v.update(OnOffType.ON);
257 assertThat((PercentType) v.getChannelState(), is(new PercentType(100)));
258 v.update(OnOffType.OFF);
259 assertThat((PercentType) v.getChannelState(), is(new PercentType(0)));
263 public void percentMQTTValue() {
264 PercentageValue v = new PercentageValue(null, null, null, null, null);
265 v.update(new DecimalType("10.10000"));
266 assertThat(v.getMQTTpublishValue(null), is("10.1"));
267 for (int i = 0; i <= 100; i++) {
268 v.update(new DecimalType(i));
269 assertThat(v.getMQTTpublishValue(null), is("" + i));
274 public void percentCustomOnOff() {
275 PercentageValue v = new PercentageValue(new BigDecimal("0.0"), new BigDecimal("100.0"), new BigDecimal("1.0"),
277 v.update(new StringType("on"));
278 assertThat((PercentType) v.getChannelState(), is(new PercentType(100)));
279 v.update(new StringType("off"));
280 assertThat((PercentType) v.getChannelState(), is(new PercentType(0)));
284 public void decimalCalc() {
285 PercentageValue v = new PercentageValue(new BigDecimal("0.1"), new BigDecimal("1.0"), new BigDecimal("0.1"),
287 v.update(new DecimalType(1.0));
288 assertThat((PercentType) v.getChannelState(), is(new PercentType(100)));
289 v.update(new DecimalType(0.1));
290 assertThat((PercentType) v.getChannelState(), is(new PercentType(0)));
291 v.update(new DecimalType(0.2));
292 assertEquals(((PercentType) v.getChannelState()).floatValue(), 11.11f, 0.01f);
296 public void increaseDecreaseCalc() {
297 PercentageValue v = new PercentageValue(new BigDecimal("1.0"), new BigDecimal("11.0"), new BigDecimal("0.5"),
301 v.update(new DecimalType("6.0"));
302 assertEquals(((PercentType) v.getChannelState()).floatValue(), 50.0f, 0.01f);
303 v.update(IncreaseDecreaseType.INCREASE);
304 assertEquals(((PercentType) v.getChannelState()).floatValue(), 55.0f, 0.01f);
305 v.update(IncreaseDecreaseType.DECREASE);
306 v.update(IncreaseDecreaseType.DECREASE);
307 assertEquals(((PercentType) v.getChannelState()).floatValue(), 45.0f, 0.01f);
310 v.update(new DecimalType("1.1"));
311 assertEquals(((PercentType) v.getChannelState()).floatValue(), 1.0f, 0.01f);
312 v.update(IncreaseDecreaseType.DECREASE);
313 assertEquals(((PercentType) v.getChannelState()).floatValue(), 0.0f, 0.01f);
316 v.update(new DecimalType("10.8"));
317 assertEquals(((PercentType) v.getChannelState()).floatValue(), 98.0f, 0.01f);
318 v.update(IncreaseDecreaseType.INCREASE);
319 assertEquals(((PercentType) v.getChannelState()).floatValue(), 100.0f, 0.01f);
323 public void upDownCalc() {
324 PercentageValue v = new PercentageValue(new BigDecimal("1.0"), new BigDecimal("11.0"), new BigDecimal("0.5"),
328 v.update(new DecimalType("6.0"));
329 assertEquals(((PercentType) v.getChannelState()).floatValue(), 50.0f, 0.01f);
330 v.update(UpDownType.UP);
331 assertEquals(((PercentType) v.getChannelState()).floatValue(), 55.0f, 0.01f);
332 v.update(UpDownType.DOWN);
333 v.update(UpDownType.DOWN);
334 assertEquals(((PercentType) v.getChannelState()).floatValue(), 45.0f, 0.01f);
337 v.update(new DecimalType("1.1"));
338 assertEquals(((PercentType) v.getChannelState()).floatValue(), 1.0f, 0.01f);
339 v.update(UpDownType.DOWN);
340 assertEquals(((PercentType) v.getChannelState()).floatValue(), 0.0f, 0.01f);
343 v.update(new DecimalType("10.8"));
344 assertEquals(((PercentType) v.getChannelState()).floatValue(), 98.0f, 0.01f);
345 v.update(UpDownType.UP);
346 assertEquals(((PercentType) v.getChannelState()).floatValue(), 100.0f, 0.01f);
350 public void percentCalcInvalid() {
351 PercentageValue v = new PercentageValue(new BigDecimal(10.0), new BigDecimal(110.0), new BigDecimal(1.0), null,
353 assertThrows(IllegalArgumentException.class, () -> v.update(new DecimalType(9.0)));