]> git.basschouten.com Git - openhab-addons.git/blob
f4bbf2bcfda7e4279f8b7f8e04f4c32902be8e98
[openhab-addons.git] /
1 /**
2  * Copyright (c) 2010-2023 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.opensprinkler.internal.api;
14
15 import static org.openhab.binding.opensprinkler.internal.OpenSprinklerBindingConstants.*;
16
17 import java.math.BigDecimal;
18 import java.util.ArrayList;
19 import java.util.List;
20
21 import org.eclipse.jdt.annotation.NonNullByDefault;
22 import org.eclipse.jetty.client.HttpClient;
23 import org.openhab.binding.opensprinkler.internal.OpenSprinklerState.JpResponse;
24 import org.openhab.binding.opensprinkler.internal.api.exception.CommunicationApiException;
25 import org.openhab.binding.opensprinkler.internal.api.exception.DataFormatErrorApiException;
26 import org.openhab.binding.opensprinkler.internal.api.exception.DataMissingApiException;
27 import org.openhab.binding.opensprinkler.internal.api.exception.GeneralApiException;
28 import org.openhab.binding.opensprinkler.internal.api.exception.MismatchApiException;
29 import org.openhab.binding.opensprinkler.internal.api.exception.NotPermittedApiException;
30 import org.openhab.binding.opensprinkler.internal.api.exception.OutOfRangeApiException;
31 import org.openhab.binding.opensprinkler.internal.api.exception.PageNotFoundApiException;
32 import org.openhab.binding.opensprinkler.internal.api.exception.UnauthorizedApiException;
33 import org.openhab.binding.opensprinkler.internal.api.exception.UnknownApiException;
34 import org.openhab.binding.opensprinkler.internal.config.OpenSprinklerHttpInterfaceConfig;
35 import org.openhab.binding.opensprinkler.internal.util.Parse;
36 import org.openhab.core.types.StateOption;
37
38 /**
39  * The {@link OpenSprinklerHttpApiV210} class is used for communicating with
40  * the OpenSprinkler API for firmware versions 2.1.0, 2.1.1 and 2.1.1
41  *
42  * @author Chris Graham - Initial contribution
43  * @author Florian Schmidt - Refactor class visibility
44  */
45 @NonNullByDefault
46 class OpenSprinklerHttpApiV210 extends OpenSprinklerHttpApiV100 {
47     /**
48      * Constructor for the OpenSprinkler API class to create a connection to the OpenSprinkler
49      * device for control and obtaining status info.
50      *
51      * @param hostname Hostname or IP address as a String of the OpenSprinkler device.
52      * @param port The port number the OpenSprinkler API is listening on.
53      * @param password Admin password for the OpenSprinkler device.
54      * @param basicUsername only needed if basic auth is required
55      * @param basicPassword only needed if basic auth is required
56      * @throws CommunicationApiException
57      * @throws Exception
58      */
59     OpenSprinklerHttpApiV210(final HttpClient httpClient, final OpenSprinklerHttpInterfaceConfig config)
60             throws GeneralApiException, CommunicationApiException {
61         super(httpClient, config);
62     }
63
64     @Override
65     public void getProgramData() throws CommunicationApiException, UnauthorizedApiException {
66         String returnContent;
67         try {
68             returnContent = http.sendHttpGet(getBaseUrl() + CMD_PROGRAM_DATA, getRequestRequiredOptions());
69         } catch (CommunicationApiException exp) {
70             throw new CommunicationApiException(
71                     "There was a problem in the HTTP communication with the OpenSprinkler API: " + exp.getMessage());
72         }
73         JpResponse resp = gson.fromJson(returnContent, JpResponse.class);
74         if (resp != null && resp.pd.length > 0) {
75             state.programs = new ArrayList<>();
76             int counter = 0;
77             for (Object x : resp.pd) {
78                 String temp = x.toString();
79                 temp = temp.substring(temp.lastIndexOf(',') + 2, temp.length() - 1);
80                 state.programs.add(new StateOption(Integer.toString(counter++), temp));
81             }
82         }
83     }
84
85     @Override
86     public List<StateOption> getStations() {
87         int counter = 0;
88         for (String x : state.jnReply.snames) {
89             state.stations.add(new StateOption(Integer.toString(counter++), x));
90         }
91         return state.stations;
92     }
93
94     @Override
95     public boolean isStationOpen(int station) throws GeneralApiException, CommunicationApiException {
96         if (state.jsReply.sn.length > 0) {
97             return state.jsReply.sn[station] == 1;
98         } else {
99             throw new GeneralApiException("There was a problem parsing the station status for the sn value.");
100         }
101     }
102
103     @Override
104     public void openStation(int station, BigDecimal duration) throws CommunicationApiException, GeneralApiException {
105         String returnContent;
106
107         try {
108             returnContent = http.sendHttpGet(getBaseUrl() + CMD_STATION_CONTROL, getRequestRequiredOptions() + "&"
109                     + CMD_STATION + station + "&" + CMD_STATION_ENABLE + "&t=" + duration);
110         } catch (CommunicationApiException exp) {
111             throw new CommunicationApiException(
112                     "There was a problem in the HTTP communication with the OpenSprinkler API: " + exp.getMessage());
113         }
114         resultParser(returnContent);
115     }
116
117     @Override
118     public void closeStation(int station) throws CommunicationApiException, GeneralApiException {
119         String returnContent;
120
121         try {
122             returnContent = http.sendHttpGet(getBaseUrl() + CMD_STATION_CONTROL,
123                     getRequestRequiredOptions() + "&" + CMD_STATION + station + "&" + CMD_STATION_DISABLE);
124         } catch (Exception exp) {
125             throw new CommunicationApiException(
126                     "There was a problem in the HTTP communication with the OpenSprinkler API: " + exp.getMessage());
127         }
128         resultParser(returnContent);
129     }
130
131     /**
132      * {@inheritDoc}
133      *
134      * @throws Exception
135      */
136     @Override
137     public void enterManualMode() throws CommunicationApiException, UnauthorizedApiException {
138         numberOfStations = getNumberOfStations();
139         isInManualMode = true;
140     }
141
142     @Override
143     public void leaveManualMode() {
144         isInManualMode = false;
145     }
146
147     /**
148      * Creates a custom exception based on a result code from the OpenSprinkler device. This is a
149      * formatted response from the API as {"result: : ##}.
150      *
151      * @param returnContent String value of the return content from the OpenSprinkler device when
152      *            an action result is returned from the API.
153      * @throws Exception Returns a custom exception based on the result key.
154      */
155     protected void resultParser(String returnContent) throws GeneralApiException {
156         int returnCode;
157
158         try {
159             returnCode = Parse.jsonInt(returnContent, JSON_OPTION_RESULT);
160         } catch (Exception exp) {
161             returnCode = -1;
162         }
163
164         switch (returnCode) {
165             case -1:
166                 throw new UnknownApiException(
167                         "The OpenSprinkler API returnd a result that was not parseable: " + returnContent);
168             case 1:
169                 return;
170             case 2:
171                 throw new UnauthorizedApiException("The OpenSprinkler API returned Unauthorized response code.");
172             case 3:
173                 throw new MismatchApiException("The OpenSprinkler API returned Mismatch response code.");
174             case 16:
175                 throw new DataMissingApiException("The OpenSprinkler API returned Data Missing response code.");
176             case 17:
177                 throw new OutOfRangeApiException("The OpenSprinkler API returned Out of Range response code.");
178             case 18:
179                 throw new DataFormatErrorApiException(
180                         "The OpenSprinkler API returned Data Format Error response code.");
181             case 32:
182                 throw new PageNotFoundApiException("The OpenSprinkler API returned Page Not Found response code.");
183             case 48:
184                 throw new NotPermittedApiException("The OpenSprinkler API returned Not Permitted response code.");
185             default:
186                 throw new UnknownApiException("Unknown response code from OpenSprinkler API: " + returnCode);
187         }
188     }
189 }