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.transform.scale.internal;
15 import static org.junit.jupiter.api.Assertions.*;
16 import static org.mockito.ArgumentMatchers.anyString;
17 import static org.mockito.ArgumentMatchers.eq;
20 import java.io.IOException;
21 import java.nio.charset.StandardCharsets;
22 import java.nio.file.Files;
23 import java.nio.file.Path;
24 import java.util.HashMap;
27 import javax.measure.quantity.Dimensionless;
29 import org.eclipse.jdt.annotation.NonNullByDefault;
30 import org.junit.jupiter.api.BeforeEach;
31 import org.junit.jupiter.api.Test;
32 import org.junit.jupiter.api.extension.ExtendWith;
33 import org.mockito.Mock;
34 import org.mockito.Mockito;
35 import org.mockito.junit.jupiter.MockitoExtension;
36 import org.mockito.junit.jupiter.MockitoSettings;
37 import org.mockito.quality.Strictness;
38 import org.mockito.stubbing.Answer;
39 import org.openhab.core.library.types.QuantityType;
40 import org.openhab.core.transform.TransformationConfiguration;
41 import org.openhab.core.transform.TransformationConfigurationRegistry;
42 import org.openhab.core.transform.TransformationException;
45 * @author Gaƫl L'hopital - Initial contribution
47 @ExtendWith(MockitoExtension.class)
48 @MockitoSettings(strictness = Strictness.LENIENT)
50 public class ScaleTransformServiceTest {
51 private static final String SRC_FOLDER = "conf" + File.separator + "transform";
54 private @NonNullByDefault({}) TransformationConfigurationRegistry transformationConfigurationRegistry;
55 private final Map<String, TransformationConfiguration> configurationMap = new HashMap<>();
56 private @NonNullByDefault({}) ScaleTransformationService processor;
59 public void init() throws IOException {
60 configurationMap.clear();
61 Files.walk(Path.of(SRC_FOLDER)).filter(Files::isRegularFile).forEach(file -> {
63 String content = new String(Files.readAllBytes(file), StandardCharsets.UTF_8);
64 String uid = Path.of(SRC_FOLDER).relativize(file).toString();
65 TransformationConfiguration transformationConfiguration = new TransformationConfiguration(uid, uid,
66 "scale", null, content);
67 configurationMap.put(uid, transformationConfiguration);
68 } catch (IOException ignored) {
72 Mockito.when(transformationConfigurationRegistry.get(anyString(), eq(null)))
73 .thenAnswer((Answer<TransformationConfiguration>) invocation -> {
74 Object[] args = invocation.getArguments();
75 return configurationMap.get(args[0]);
77 processor = new ScaleTransformationService(transformationConfigurationRegistry);
81 public void testTransformByScale() throws TransformationException {
82 // need to be sure we'll have the german version
83 String existingscale = "scale/humidex_de.scale";
85 String transformedResponse = processor.transform(existingscale, source);
86 assertEquals("nicht wesentlich", transformedResponse);
88 existingscale = "scale/limits.scale";
90 transformedResponse = processor.transform(existingscale, source);
91 assertEquals("middle", transformedResponse);
95 public void testTransformByScaleLimits() throws TransformationException {
96 String existingscale = "scale/limits.scale";
98 // Testing upper bound opened range
99 String source = "500";
100 String transformedResponse = processor.transform(existingscale, source);
101 assertEquals("extreme", transformedResponse);
103 // Testing lower bound opened range
105 transformedResponse = processor.transform(existingscale, source);
106 assertEquals("low", transformedResponse);
108 // Testing unfinite up and down range
109 existingscale = "scale/catchall.scale";
111 transformedResponse = processor.transform(existingscale, source);
112 assertEquals("catchall", transformedResponse);
116 public void testTransformByScaleUndef() throws TransformationException {
117 // check that for undefined/non numeric value we return empty string
119 String existingscale = "scale/humidex_fr.scale";
121 assertThrows(TransformationException.class, () -> processor.transform(existingscale, source));
125 public void testTransformByScaleErrorInBounds() throws TransformationException {
126 // the tested file contains inputs that generate a conversion error of the bounds
128 String existingscale = "scale/erroneous.scale";
129 String source = "15";
131 @SuppressWarnings("unused")
132 String transformedResponse = processor.transform(existingscale, source);
134 } catch (TransformationException e) {
140 public void testTransformByScaleErrorInValue() throws TransformationException {
141 // checks that an error is raised when trying to scale an erroneous value
142 String existingscale = "scale/evaluationorder.scale";
143 String source = "azerty";
144 assertThrows(TransformationException.class, () -> processor.transform(existingscale, source));
148 public void testEvaluationOrder() throws TransformationException {
149 // Ensures that only first matching scale as presented in the file is taken in account
150 String evaluationOrder = "scale/evaluationorder.scale";
151 // This value matches two lines of the scale file
152 String source = "12";
154 String transformedResponse = processor.transform(evaluationOrder, source);
155 assertEquals("first", transformedResponse);
159 public void testTransformQuantityType() throws TransformationException {
160 QuantityType<Dimensionless> airQuality = new QuantityType<>("992 ppm");
161 String aqScaleFile = "scale/netatmo_aq.scale";
162 String expected = "Correcte (992 ppm) !";
164 String transformedResponse = processor.transform(aqScaleFile, airQuality.toString());
165 assertEquals(expected, transformedResponse);
169 public void testCatchNonNumericValue() throws TransformationException {
170 // checks that an error is raised when trying to scale an erroneous value
171 String existingscale = "scale/catchnonnumeric.scale";
172 String source = "azerty";
173 String transformedResponse = processor.transform(existingscale, source);
174 assertEquals("Non Numeric", transformedResponse);
178 public void testTransformAndFormat() throws TransformationException {
179 String existingscale = "scale/netatmo_aq.scale";
180 String source = "992";
181 String transformedResponse = processor.transform(existingscale, source);
182 assertEquals("Correcte (992) !", transformedResponse);
186 public void testValueExceedsRange() throws TransformationException {
187 String existingscale = "scale/humidex.scale";
188 String source = "200";
189 assertThrows(TransformationException.class, () -> processor.transform(existingscale, source));