]> git.basschouten.com Git - openhab-addons.git/blob
cc8499e4e6b11b2230628faddaeefacdb06a2e85
[openhab-addons.git] /
1 /**
2  * Copyright (c) 2010-2024 Contributors to the openHAB project
3  *
4  * See the NOTICE file(s) distributed with this work for additional
5  * information.
6  *
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
10  *
11  * SPDX-License-Identifier: EPL-2.0
12  */
13 package org.openhab.binding.sensorcommunity.internal.handler;
14
15 import static org.openhab.binding.sensorcommunity.internal.utils.Constants.*;
16
17 import java.time.LocalDateTime;
18 import java.util.List;
19 import java.util.Objects;
20 import java.util.concurrent.TimeUnit;
21
22 import org.eclipse.jdt.annotation.NonNullByDefault;
23 import org.eclipse.jdt.annotation.Nullable;
24 import org.eclipse.jetty.client.HttpClient;
25 import org.eclipse.jetty.client.api.Request;
26 import org.eclipse.jetty.client.util.BufferingResponseListener;
27 import org.openhab.binding.sensorcommunity.internal.dto.SensorData;
28 import org.openhab.binding.sensorcommunity.internal.dto.SensorDataValue;
29 import org.openhab.binding.sensorcommunity.internal.utils.DateTimeUtils;
30 import org.slf4j.Logger;
31 import org.slf4j.LoggerFactory;
32
33 import com.google.gson.Gson;
34
35 /**
36  * The {@link HTTPHandler} is responsible for HTTP requests and JSON handling
37  *
38  * @author Bernd Weymann - Initial contribution
39  */
40 @NonNullByDefault
41 public class HTTPHandler {
42     private final Logger logger = LoggerFactory.getLogger(HTTPHandler.class);
43
44     private static final Gson GSON = new Gson();
45     private static final HTTPHandler HTTP_HANDLER = new HTTPHandler();
46
47     private static @Nullable HttpClient commonHttpClient;
48
49     public static void init(HttpClient httpClient) {
50         commonHttpClient = httpClient;
51     }
52
53     public static HTTPHandler getHandler() {
54         return HTTP_HANDLER;
55     }
56
57     public synchronized void request(String url, BaseSensorHandler callback) {
58         HttpClient localClient = commonHttpClient;
59         if (localClient == null) {
60             logger.warn("HTTP Client not initialized");
61         } else {
62             Request req = localClient.newRequest(url);
63             req.timeout(15, TimeUnit.SECONDS).send(new BufferingResponseListener() {
64                 @NonNullByDefault({})
65                 @Override
66                 public void onComplete(org.eclipse.jetty.client.api.Result result) {
67                     if (result.getResponse().getStatus() != 200) {
68                         String failure;
69                         if (result.getResponse().getReason() != null) {
70                             failure = result.getResponse().getReason();
71                         } else {
72                             failure = result.getFailure().getMessage();
73                         }
74                         callback.onError(Objects.requireNonNullElse(failure, "Unknown error"));
75                     } else {
76
77                         callback.onResponse(Objects.requireNonNull(getContentAsString()));
78                     }
79                 }
80             });
81         }
82     }
83
84     public @Nullable List<SensorDataValue> getLatestValues(String response) {
85         SensorData[] valueArray = GSON.fromJson(response, SensorData[].class);
86         if (valueArray.length == 0) {
87             return null;
88         } else if (valueArray.length == 1) {
89             SensorData v = valueArray[0];
90             return v.getSensorDataValues();
91         } else if (valueArray.length > 1) {
92             // declare first item as latest
93             SensorData latestData = valueArray[0];
94             String latestTimeStr = latestData.getTimeStamp();
95             LocalDateTime latestTime = DateTimeUtils.toDate(latestTimeStr);
96             if (latestTime == null) {
97                 logDateConversionError(response, latestData);
98             }
99             for (int i = 1; i < valueArray.length; i++) {
100                 SensorData iterData = valueArray[i];
101                 String iterTimeStr = iterData.getTimeStamp();
102                 LocalDateTime iterTime = DateTimeUtils.toDate(iterTimeStr);
103                 if (iterTime == null) {
104                     logDateConversionError(response, latestData);
105                 }
106                 if (iterTime != null && latestTime != null) {
107                     if (latestTime.isBefore(iterTime)) {
108                         // found item is newer - take it as latest
109                         latestTime = iterTime;
110                         latestData = iterData;
111                     } // else - found item is older - nothing to do
112                 } else {
113                     logger.warn("One or two dates cannot be decoded 1) {} 2) {}", iterTimeStr, latestTimeStr);
114                 }
115             }
116             return latestData.getSensorDataValues();
117         } else {
118             return null;
119         }
120     }
121
122     public void logDateConversionError(final String response, final Object dto) {
123         logger.warn("Unable to get timestamp");
124         logger.warn("Response: {}", response);
125         String json = GSON.toJson(dto);
126         logger.warn("GSon: {}", json);
127     }
128
129     public boolean isParticulate(@Nullable List<SensorDataValue> valueList) {
130         if (valueList == null) {
131             return false;
132         }
133         return valueList.stream().map(v -> v.getValueType()).filter(t -> t.endsWith(P1) || t.endsWith(P2)).findAny()
134                 .isPresent();
135     }
136
137     public boolean isCondition(@Nullable List<SensorDataValue> valueList) {
138         if (valueList == null) {
139             return false;
140         }
141         return valueList.stream().map(v -> v.getValueType()).filter(t -> t.equals(TEMPERATURE) || t.endsWith(HUMIDITY)
142                 || t.endsWith(PRESSURE) || t.endsWith(PRESSURE_SEALEVEL)).findAny().isPresent();
143     }
144
145     public boolean isNoise(@Nullable List<SensorDataValue> valueList) {
146         if (valueList == null) {
147             return false;
148         }
149         return valueList.stream().map(v -> v.getValueType())
150                 .filter(t -> t.endsWith(NOISE_EQ) || t.endsWith(NOISE_MAX) || t.endsWith(NOISE_MIN)).findAny()
151                 .isPresent();
152     }
153 }