Imported Upstream version 1.0.0
[platform/upstream/iotivity.git] / service / resource-encapsulation / examples / linux / SampleResourceServer.cpp
1 /******************************************************************
2  *
3  * Copyright 2015 Samsung Electronics All Rights Reserved.
4  *
5  *
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  ******************************************************************/
20
21 #include "PrimitiveResource.h"
22 #include "RCSResourceObject.h"
23 #include "OCPlatform.h"
24 #include "OCApi.h"
25
26 using namespace OC;
27 using namespace OC::OCPlatform;
28 using namespace OIC::Service;
29
30 constexpr int DEFALUT_VALUE = 0;
31
32 constexpr int REQUEST_TEMP = 1;
33 constexpr int REQUEST_LIGHT = 2;
34
35 constexpr int PRESENCE_ON = 1;
36 constexpr int PRESENCE_OFF = 2;
37
38 constexpr int DEFALUT_SERVER = 1;
39 constexpr int CUSTOM_SERVER = 2;
40 constexpr int STOP = 3;
41
42 constexpr int INCREASE_TEMPERATURE = 1;
43 constexpr int DECREASE_TEMPERATURE = 2;
44 constexpr int STOP_TEMPERATURE_SENSOR = 3;
45
46 constexpr int INCREASE_BRIGHTNESS = 1;
47 constexpr int DECREASE_BRIGHTNESS = 2;
48 constexpr int STOP_LIGHT_SENSOR = 3;
49
50 constexpr int CORRECT_INPUT = 1;
51 constexpr int INCORRECT_INPUT = 2;
52 constexpr int QUIT = 3;
53
54
55 std::string resourceType = "oic.r.temperaturesensor";
56 std::string resourceInterface = "oic.if.";
57 std::string resourceUri;
58 std::string attributeKey;
59 int isPresenceOn = PRESENCE_ON;
60
61 RCSResourceObject::Ptr server;
62
63 int processUserInput();
64
65 enum class Control{
66     INCREASE,
67     DECREASE
68 };
69
70 void displayMenu()
71 {
72     std::cout << "====================================================================="
73               << std::endl;
74     std::cout << "   1 - Creation of Resource [Auto control for requests]" << std::endl;
75     std::cout << "   2 - Creation of Resource [Developer control for Get and Set requests]"
76               << std::endl;
77     std::cout << "   3 - Quit" << std::endl;
78     std::cout << "====================================================================="
79               << std::endl;
80 }
81
82 void displayResourceTypeMenu()
83 {
84     std::cout << "========================================================" << std::endl;
85     std::cout << "Select Resource Type" << std::endl;
86     std::cout << "1. Temperature" << std::endl;
87     std::cout << "2. Light" << std::endl;
88     std::cout << "========================================================" << std::endl;
89 }
90
91 void displayControlTemperatureMenu()
92 {
93     std::cout << "========================================================" << std::endl;
94     std::cout << "1. Increase Temperature by 1 degree" << std::endl;
95     std::cout << "2. Decrease Temperature by 1 degree" << std::endl;
96     std::cout << "3. Stop the Sensor" << std::endl;
97     std::cout << "========================================================" << std::endl;
98 }
99
100 void displayControlLightMenu()
101 {
102     std::cout << "========================================================" << std::endl;
103     std::cout << "1. Increase Brightness by 1 stage" << std::endl;
104     std::cout << "2. Decrease Brightness by 1 stage" << std::endl;
105     std::cout << "3. Stop the Sensor" << std::endl;
106     std::cout << "========================================================" << std::endl;
107 }
108
109 void printAttribute(const RCSResourceAttributes& attrs)
110 {
111     for(const auto& attr : attrs)
112     {
113         std::cout << "\tkey : " << attr.key() << "\n\tvalue : "
114                   << attr.value().toString() << std::endl;
115     }
116 }
117
118 //hander for get request (if developer choose second option for resource Creation)
119 RCSGetResponse requestHandlerForGet(const RCSRequest& request,
120         RCSResourceAttributes& attrs)
121 {
122     std::cout << "Received a Get request from Client" << std::endl;
123     RCSResourceObject::LockGuard lock(*server);
124     RCSResourceAttributes attributes = server->getAttributes();
125
126     std::cout << "\nSending response to Client : " << std::endl;
127     printAttribute(attributes);
128
129     return RCSGetResponse::defaultAction();
130 }
131
132 //hander for set request (if developer choose second option for resource Creation)
133 RCSSetResponse requestHandlerForSet(const RCSRequest& request,
134         RCSResourceAttributes& attrs)
135 {
136     std::cout << "Received a Set request from Client" << std::endl;
137
138     std::cout << "\n\nSending response to Client : " << std::endl;
139     RCSResourceObject::LockGuard lock(*server);
140     printAttribute(attrs);
141     return RCSSetResponse::defaultAction();
142 }
143
144 void createResource()
145 {
146     server = RCSResourceObject::Builder(resourceUri, resourceType,resourceInterface).
147             setDiscoverable(true).setObservable(true).build();
148 }
149
150 void initServer()
151 {
152     try
153     {
154         createResource();
155     }
156     catch (const RCSPlatformException& e)
157     {
158         std::cout << "Exception in initServer : " << e.what() << std::endl;
159     }
160
161     server->setAutoNotifyPolicy(RCSResourceObject::AutoNotifyPolicy::UPDATED);
162     server->setSetRequestHandlerPolicy(RCSResourceObject::SetRequestHandlerPolicy::NEVER);
163     server->setAttribute(attributeKey, DEFALUT_VALUE);
164 }
165
166 void changeAttribute(Control control)
167 {
168     RCSResourceObject::LockGuard lock(server);
169     if(Control::INCREASE == control)
170     {
171         server->getAttributes()[attributeKey] =
172                 server->getAttribute<int>(attributeKey) + 1;
173         std::cout << attributeKey << " increased." << std::endl;
174     }
175     else if(Control::DECREASE == control)
176     {
177         server->getAttributes()[attributeKey] =
178                         server->getAttribute<int>(attributeKey) - 1;
179         std::cout << attributeKey << " Decreased." << std::endl;
180     }
181     std::cout << "\nCurrent " << attributeKey << ": "
182             << server->getAttributeValue(attributeKey).get<int>() << std::endl;
183 }
184
185 int processUserInput()
186 {
187     int userInput;
188     std::cin >> userInput;
189     if (std::cin.fail())
190     {
191         std::cin.clear();
192         std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
193         return -1;
194     }
195     return userInput;
196 }
197
198 int selectPresenceMenu()
199 {
200     std::cout << "========================================================" << std::endl;
201     std::cout << "1. Presence On" << std::endl;
202     std::cout << "2. Presence Off" << std::endl;
203     std::cout << "========================================================" << std::endl;
204
205     switch(processUserInput())
206         {
207         case PRESENCE_ON:
208             isPresenceOn = PRESENCE_ON;
209             startPresence(3);
210             return CORRECT_INPUT;
211         case PRESENCE_OFF:
212             isPresenceOn = PRESENCE_OFF;
213             return CORRECT_INPUT;
214         default :
215             std::cout << "Invalid input, please try again" << std::endl;
216             return INCORRECT_INPUT;
217         }
218 }
219
220 int selectResourceTypeMenu()
221 {
222     displayResourceTypeMenu();
223
224     switch(processUserInput())
225     {
226         case REQUEST_TEMP:
227             resourceUri = "/a/TempSensor";
228             resourceType = "oic.r.temperaturesensor";
229             attributeKey = "Temperature";
230             return CORRECT_INPUT;
231         case REQUEST_LIGHT:
232             resourceUri = "/a/light";
233             resourceType = "oic.r.light";
234             attributeKey = "Brightness";
235             return CORRECT_INPUT;
236         default :
237             std::cout << "Invalid input, please try again" << std::endl;
238             return INCORRECT_INPUT;
239     }
240 }
241
242 int selectServerMenu()
243 {
244     switch (processUserInput())
245     {
246         case DEFALUT_SERVER: // Creation of Resource & Auto control for all requests from Client.
247             while(true)
248             {
249                 int ret = selectResourceTypeMenu();
250                 if(ret == CORRECT_INPUT) break;
251             }
252             initServer();
253             return CORRECT_INPUT;
254
255         case CUSTOM_SERVER:
256             // Creation of Resource & setting get and set handler for handling get and
257             // set request from client in application.
258             while(true)
259             {
260                 int ret = selectResourceTypeMenu();
261                 if(ret == CORRECT_INPUT) break;
262             }
263             initServer();
264
265             server->setGetRequestHandler(requestHandlerForGet);
266             server->setSetRequestHandler(requestHandlerForSet);
267             return CORRECT_INPUT;
268         case STOP :
269             return QUIT;
270
271         default :
272             std::cout << "Invalid input, please try again" << std::endl;
273             return INCORRECT_INPUT;
274     }
275 }
276
277 int selectControlTemperatureMenu()
278 {
279     displayControlTemperatureMenu();
280
281     switch (processUserInput())
282     {
283        case INCREASE_TEMPERATURE:
284            changeAttribute(Control::INCREASE);
285            return CORRECT_INPUT;
286
287        case DECREASE_TEMPERATURE:
288            changeAttribute(Control::DECREASE);
289            return CORRECT_INPUT;
290
291        case STOP_TEMPERATURE_SENSOR:
292            return QUIT;
293
294        default:
295            std::cout << "Invalid input. Please try again." << std::endl;
296            return INCORRECT_INPUT;
297    }
298 }
299
300 int selectControlLightMenu()
301 {
302     displayControlLightMenu();
303
304     switch (processUserInput())
305     {
306         case INCREASE_BRIGHTNESS:
307             changeAttribute(Control::INCREASE);
308             return CORRECT_INPUT;
309
310         case DECREASE_BRIGHTNESS:
311             changeAttribute(Control::DECREASE);
312             return CORRECT_INPUT;
313
314         case STOP_LIGHT_SENSOR:
315             return QUIT;
316
317         default:
318             std::cout << "Invalid input. Please try again." << std::endl;
319             return INCORRECT_INPUT;
320     }
321 }
322
323 void process()
324 {
325     while(true)
326     {
327         int ret = selectPresenceMenu();
328         if(ret == CORRECT_INPUT) break;
329     }
330
331     while(true)
332     {
333         displayMenu();
334         int ret = selectServerMenu();
335
336         if(ret == QUIT) return;
337         if(ret == CORRECT_INPUT) break;
338     }
339
340     while(true)
341     {
342         if(resourceType == "oic.r.temperaturesensor")
343         {
344             int ret = selectControlTemperatureMenu();
345             if (ret == QUIT) return;
346             if (ret == INCORRECT_INPUT) continue;
347         }
348         else if(resourceType == "oic.r.light")
349         {
350             int ret = selectControlLightMenu();
351             if (ret == QUIT) return;
352             if (ret == INCORRECT_INPUT) continue;
353         }
354     }
355 }
356
357 int main(void)
358 {
359     try
360     {
361         process();
362         server = NULL;
363
364         if(isPresenceOn == PRESENCE_ON)
365         {
366             stopPresence();
367         }
368     }
369     catch (const std::exception& e)
370     {
371         std::cout << "main exception  : " << e.what() << std::endl;
372     }
373     std::cout << "Stopping the Server" << std::endl;
374 }
375