]> git.basschouten.com Git - openhab-addons.git/blob
2ba61fc1643b698043192aa7b0c33169ee6d232e
[openhab-addons.git] /
1 /**
2  * Copyright (c) 2010-2020 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
14 package org.openhab.binding.touchwand.internal;
15
16 import static org.openhab.binding.touchwand.internal.TouchWandBindingConstants.*;
17
18 import java.io.UnsupportedEncodingException;
19 import java.net.CookieManager;
20 import java.net.MalformedURLException;
21 import java.net.URL;
22 import java.net.URLEncoder;
23 import java.nio.charset.StandardCharsets;
24 import java.util.HashMap;
25 import java.util.Map;
26 import java.util.concurrent.ExecutionException;
27 import java.util.concurrent.TimeUnit;
28 import java.util.concurrent.TimeoutException;
29
30 import org.eclipse.jdt.annotation.NonNullByDefault;
31 import org.eclipse.jetty.client.HttpClient;
32 import org.eclipse.jetty.client.api.ContentProvider;
33 import org.eclipse.jetty.client.api.ContentResponse;
34 import org.eclipse.jetty.client.api.Request;
35 import org.eclipse.jetty.client.util.StringContentProvider;
36 import org.eclipse.jetty.http.HttpMethod;
37 import org.eclipse.jetty.http.MimeTypes;
38 import org.openhab.core.library.types.OnOffType;
39 import org.slf4j.Logger;
40 import org.slf4j.LoggerFactory;
41
42 /**
43  * The {@link TouchWandRestClient} is responsible for handling low level commands units TouchWand WonderFull hub
44  * REST API interface
45  *
46  * @author Roie Geron - Initial contribution
47  */
48 @NonNullByDefault
49 public class TouchWandRestClient {
50
51     private final Logger logger = LoggerFactory.getLogger(TouchWandRestClient.class);
52
53     static CookieManager cookieManager = new CookieManager();
54
55     private static final HttpMethod METHOD_GET = HttpMethod.GET;
56     private static final HttpMethod METHOD_POST = HttpMethod.POST;
57
58     private static final String CMD_LOGIN = "login";
59     private static final String CMD_LIST_UNITS = "listunits";
60     private static final String CMD_LIST_SCENARIOS = "listsencarios";
61     private static final String CMD_UNIT_ACTION = "action";
62     private static final String CMD_GET_UNIT_BY_ID = "getunitbyid";
63
64     private static final String ACTION_SWITCH_OFF = "{\"id\":%s,\"value\":" + SWITCH_STATUS_OFF + "}";
65     private static final String ACTION_SWITCH_ON = "{\"id\":%s,\"value\":" + SWITCH_STATUS_ON + "}";
66     private static final String ACTION_SHUTTER_DOWN = "{\"id\":%s,\"value\":0,\"type\":\"height\"}";
67     private static final String ACTION_SHUTTER_UP = "{\"id\":%s,\"value\":255,\"type\":\"height\"}";
68     private static final String ACTION_SHUTTER_STOP = "{\"id\":%s,\"value\":0,\"type\":\"stop\"}";
69     private static final String ACTION_SHUTTER_POSITION = "{\"id\":%s,\"value\":%s}";
70     private static final String ACTION_DIMMER_POSITION = "{\"id\":%s,\"value\":%s}";
71
72     private static final String CONTENT_TYPE_APPLICATION_JSON = MimeTypes.Type.APPLICATION_JSON.asString();
73
74     private static final int REQUEST_TIMEOUT_SEC = 10;
75
76     private static final Map<String, String> COMMAND_MAP = new HashMap<String, String>();
77     static {
78         COMMAND_MAP.put(CMD_LOGIN, "/auth/login?");
79         COMMAND_MAP.put(CMD_LIST_UNITS, "/units/listUnits");
80         COMMAND_MAP.put(CMD_LIST_SCENARIOS, "/scenarios/listScenarios");
81         COMMAND_MAP.put(CMD_UNIT_ACTION, "/units/action");
82         COMMAND_MAP.put(CMD_GET_UNIT_BY_ID, "/units/getUnitByID?");
83     }
84
85     private String touchWandIpAddr = "";
86     private String touchWandPort = "";
87     private boolean isConnected = false;
88     private HttpClient httpClient;
89
90     public TouchWandRestClient(HttpClient httpClient) {
91         this.httpClient = httpClient;
92     }
93
94     public final boolean connect(String user, String pass, String ipAddr, String port) {
95         touchWandIpAddr = ipAddr;
96         touchWandPort = port;
97         isConnected = cmdLogin(user, pass, ipAddr);
98
99         return isConnected;
100     }
101
102     private final boolean cmdLogin(String user, String pass, String ipAddr) {
103         String encodedUser;
104         String encodedPass;
105         String response = "";
106
107         try {
108             encodedUser = URLEncoder.encode(user, StandardCharsets.UTF_8.toString());
109             encodedPass = URLEncoder.encode(pass, StandardCharsets.UTF_8.toString());
110             String command = buildUrl(CMD_LOGIN) + "user=" + encodedUser + "&" + "psw=" + encodedPass;
111             response = sendCommand(command, METHOD_GET, "");
112         } catch (UnsupportedEncodingException e) {
113             logger.warn("Error url encoding username or password : {}", e.getMessage());
114         }
115
116         return !response.equals("Unauthorized");
117     }
118
119     public String cmdListUnits() {
120         String response = "";
121         if (isConnected) {
122             String command = buildUrl(CMD_LIST_UNITS);
123             response = sendCommand(command, METHOD_GET, "");
124         }
125         return response;
126     }
127
128     public String cmdGetUnitById(String id) {
129         String response = "";
130
131         if (isConnected) {
132             String command = buildUrl(CMD_GET_UNIT_BY_ID) + "id=" + id;
133             response = sendCommand(command, METHOD_GET, "");
134         }
135         return response;
136     }
137
138     public void cmdSwitchOnOff(String id, OnOffType onoff) {
139         String action;
140
141         if (OnOffType.OFF.equals(onoff)) {
142             action = String.format(ACTION_SWITCH_OFF, id);
143         } else {
144             action = String.format(ACTION_SWITCH_ON, id);
145         }
146         cmdUnitAction(action);
147     }
148
149     public void cmdShutterUp(String id) {
150         String action = String.format(ACTION_SHUTTER_UP, id);
151         cmdUnitAction(action);
152     }
153
154     public void cmdShutterDown(String id) {
155         String action = String.format(ACTION_SHUTTER_DOWN, id);
156         cmdUnitAction(action);
157     }
158
159     public void cmdShutterPosition(String id, String position) {
160         String action = String.format(ACTION_SHUTTER_POSITION, id, position);
161         cmdUnitAction(action);
162     }
163
164     public void cmdShutterStop(String id) {
165         String action = String.format(ACTION_SHUTTER_STOP, id);
166         cmdUnitAction(action);
167     }
168
169     public void cmdDimmerPosition(String id, String position) {
170         String action = String.format(ACTION_DIMMER_POSITION, id, position);
171         cmdUnitAction(action);
172     }
173
174     private String cmdUnitAction(String action) {
175         String response = "";
176         if (isConnected) {
177             String command = buildUrl(CMD_UNIT_ACTION);
178             response = sendCommand(command, METHOD_POST, action);
179         }
180         return response;
181     }
182
183     private String buildUrl(String command) {
184         String url = "http://" + touchWandIpAddr + ":" + touchWandPort + COMMAND_MAP.get(command);
185         return url;
186     }
187
188     private synchronized String sendCommand(String command, HttpMethod method, String content) {
189         ContentResponse response;
190         Request request;
191
192         URL url = null;
193         try {
194             url = new URL(command);
195         } catch (MalformedURLException e) {
196             logger.warn("Error building URL {} : {}", command, e.getMessage());
197             return "";
198         }
199
200         request = httpClient.newRequest(url.toString()).timeout(REQUEST_TIMEOUT_SEC, TimeUnit.SECONDS).method(method);
201         if (method.equals(METHOD_POST) && (!content.isEmpty())) {
202             ContentProvider contentProvider = new StringContentProvider(CONTENT_TYPE_APPLICATION_JSON, content,
203                     StandardCharsets.UTF_8);
204             request = request.content(contentProvider);
205         }
206
207         try {
208             response = request.send();
209             return response.getContentAsString();
210         } catch (InterruptedException | TimeoutException | ExecutionException e) {
211             logger.warn("Error opening connecton to {} : {} ", touchWandIpAddr, e.getMessage());
212         }
213         return "";
214     }
215 }