replace : iotivity -> iotivity-sec
[platform/upstream/iotivity.git] / service / notification / cpp-wrapper / unittest / NSProviderServiceSimulator.h
1 //******************************************************************
2 //
3 // Copyright 2016 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 #ifndef _NS_PROVIDER_SERVICE_SIMULATOR_H_
22 #define _NS_PROVIDER_SERVICE_SIMULATOR_H_
23
24 #include <iostream>
25 #include <memory>
26
27 #include "OCPlatform.h"
28 #include "OCApi.h"
29 #include "OCResourceResponse.h"
30
31 namespace
32 {
33     enum class requestType
34     {
35         NS_NOTIFICATION,
36         NS_MESSAGE,
37         NS_SYNC,
38         NS_TOPIC,
39     };
40     enum class messageType
41     {
42         NS_ALLOW = 1,
43         NS_DENY,
44         NS_TOPIC,
45     };
46 }
47
48 class NSProviderSimulator
49 {
50     public:
51         enum class TopicAllowState
52         {
53             DENY,
54             ALLOW
55         };
56         typedef std::pair<std::string, TopicAllowState> NS_TopicState;
57         typedef std::map<std::string, TopicAllowState> NS_TopicStateList;
58
59         typedef std::list<std::string> NS_TopicList;
60     private:
61         OCResourceHandle m_notificationHandle;
62         OCResourceHandle m_messageHandle;
63         OCResourceHandle m_syncHandle;
64         OCResourceHandle m_topicHandle;
65         OC::OCRepresentation m_syncRep;
66         OC::OCRepresentation m_messageRep;
67         int m_accepter;
68
69         std::string m_notificationUri;
70         std::string m_messageUri;
71         std::string m_syncUri;
72         std::string m_topicUri;
73         NS_TopicList m_topicList;
74         NS_TopicStateList m_allowedTopicList;
75
76         OC::ObservationIds m_syncObservers;
77
78     public:
79         NSProviderSimulator()
80             : m_notificationHandle(), m_messageHandle(), m_syncHandle(), m_topicHandle(),
81               m_syncRep(), m_messageRep(), m_accepter(0),
82               m_notificationUri(std::string("/notification")),
83               m_messageUri(std::string("/message")),
84               m_syncUri(std::string("/sync")),
85               m_topicUri(std::string("/topic")),
86               m_topicList(),
87               m_allowedTopicList(),
88               m_syncObservers()
89         {
90
91         };
92
93         ~NSProviderSimulator() = default;
94
95         NSProviderSimulator(const NSProviderSimulator &) = delete;
96         NSProviderSimulator &operator = (const NSProviderSimulator &) = delete;
97
98         NSProviderSimulator(NSProviderSimulator &&) = delete;
99         NSProviderSimulator &operator = (NSProviderSimulator &&) = delete;
100
101     private:
102         std::shared_ptr<OC::OCResourceResponse> getResponse(
103             std::shared_ptr< OC::OCResourceRequest > requests, requestType type)
104         {
105             auto response = std::make_shared<OC::OCResourceResponse>();
106             response->setRequestHandle(requests->getRequestHandle());
107             response->setResourceHandle(requests->getResourceHandle());
108
109             int requestFlag = requests->getRequestHandlerFlag();
110             if (requestFlag == OC::RequestHandlerFlag::RequestFlag)
111             {
112                 std::string request = requests->getRequestType();
113
114             response->setErrorCode(200);
115                 response->setResponseResult(OC_EH_OK);
116
117                 if (request == "GET")
118                 {
119                     OC::OCRepresentation rep;
120
121                     if (type == requestType::NS_NOTIFICATION)
122                     {
123                         std::string msgUri = m_notificationUri + m_messageUri;
124                         std::string syncUri = m_notificationUri + m_syncUri;
125                         std::string topicUri = m_notificationUri + m_topicUri;
126                         std::string providerId = "123456789012345678901234567890123456";
127                         rep.setValue("x.org.iotivity.ns.subcontrollability", m_accepter);
128                         rep.setValue("x.org.iotivity.ns.messageuri", msgUri);
129                         rep.setValue("x.org.iotivity.ns.syncuri", syncUri);
130                         rep.setValue("x.org.iotivity.ns.topicuri", topicUri);
131                         rep.setValue("x.org.iotivity.ns.providerid", providerId);
132                     }
133                     else if (type == requestType::NS_SYNC)
134                     {
135                         rep = m_syncRep;
136                     }
137                     else if (type == requestType::NS_MESSAGE)
138                     {
139                         rep = m_messageRep;
140                     }
141                     else if (type == requestType::NS_TOPIC)
142                     {
143                         if (m_allowedTopicList.empty())
144                         {
145                             std::for_each (m_topicList.begin(), m_topicList.end(),
146                                            [this](const std::string & topic)
147                             {
148                                 m_allowedTopicList.insert(
149                                     std::make_pair<std::string, TopicAllowState>(
150                                         std::string(topic), TopicAllowState::DENY));
151                             }
152                                           );
153                         }
154
155                         std::vector<OC::OCRepresentation> topicArr;
156
157                         std::for_each (m_allowedTopicList.begin(), m_allowedTopicList.end(),
158                                        [& topicArr](const NS_TopicState & topicState)
159                         {
160                             OC::OCRepresentation topic;
161                             topic.setValue("x.org.iotivity.ns.topicname", topicState.first);
162                             topic.setValue("x.org.iotivity.ns.topicstate", (int) topicState.second);
163                             topicArr.push_back(topic);
164                         }
165                                       );
166
167                         rep.setValue<std::vector<OC::OCRepresentation>>
168                                 ("x.org.iotivity.ns.topiclist", topicArr);
169                     }
170                     else
171                     {
172                         return NULL;
173                     }
174
175                     response->setResourceRepresentation(rep);
176                     return response;
177                 }
178
179                 else if (request == "POST")
180                 {
181                     if (type == requestType::NS_SYNC)
182                     {
183                         m_syncRep = requests->getResourceRepresentation();
184
185                         std::cout << "Receive POST for Sync" << std::endl;
186                         std::cout << "provider Id : " << m_syncRep.getValueToString("x.org.iotivity.ns.providerid") << std::endl;
187                         std::cout << "Sync State : " << m_syncRep.getValueToString("x.org.iotivity.ns.state") << std::endl;
188
189                         response->setResourceRepresentation(m_syncRep);
190
191                         OC::OCPlatform::notifyAllObservers(m_syncHandle);
192
193                         return response;
194                     }
195                     else if (type == requestType::NS_TOPIC)
196                     {
197                         auto receivePayload =
198                             requests->getResourceRepresentation()
199                             .getValue<std::vector<OC::OCRepresentation>>("x.org.iotivity.ns.topiclist");
200
201                         std::for_each (receivePayload.begin(), receivePayload.end(),
202                                        [this](const OC::OCRepresentation & rep)
203                         {
204                             auto tmp = m_allowedTopicList.find(rep.getValueToString("x.org.iotivity.ns.topicname"));
205                             if (tmp != m_allowedTopicList.end())
206                             {
207                                 tmp->second = (TopicAllowState) rep.getValue<int>("x.org.iotivity.ns.topicstate");
208                             }
209                         }
210                                       );
211                     }
212                 }
213             }
214
215             return NULL;
216         }
217
218         void setObserver(std::shared_ptr< OC::OCResourceRequest > requests, requestType type)
219         {
220             if (type == requestType::NS_SYNC)
221             {
222                 OC::ObservationInfo observationInfo = requests->getObservationInfo();
223                 if (OC::ObserveAction::ObserveRegister == observationInfo.action)
224                 {
225                     m_syncObservers.push_back(observationInfo.obsId);
226                 }
227                 else if (OC::ObserveAction::ObserveUnregister == observationInfo.action)
228                 {
229                     m_syncObservers.erase(std::remove(
230                                               m_syncObservers.begin(), m_syncObservers.end(),
231                                               observationInfo.obsId), m_syncObservers.end());
232                 }
233             }
234             else if (type == requestType::NS_MESSAGE)
235             {
236                 OC::OCRepresentation rep;
237                 std::string providerId = "123456789012345678901234567890123456";
238                 rep.setValue<int>("x.org.iotivity.ns.messageid", (int)messageType::NS_ALLOW);
239                 rep.setValue("x.org.iotivity.ns.providerid", providerId);
240
241                 auto response = std::make_shared<OC::OCResourceResponse>();
242                 response->setRequestHandle(requests->getRequestHandle());
243                 response->setResourceHandle(requests->getResourceHandle());
244             response->setErrorCode(200);
245                 response->setResponseResult(OC_EH_OK);
246                 response->setResourceRepresentation(rep);
247
248                 OC::ObservationIds ids;
249                 ids.push_back(requests->getObservationInfo().obsId);
250
251                 OC::OCPlatform::notifyListOfObservers(m_messageHandle, ids, response);
252             }
253         }
254
255         OCEntityHandlerResult entityHandler(
256             std::shared_ptr< OC::OCResourceRequest > request, requestType type)
257         {
258             if (!request)
259             {
260                 return OC_EH_ERROR;
261             }
262
263             std::cout << "Provider : Income request : " << request->getRequestHandlerFlag() << std::endl;
264             if ((request->getRequestHandlerFlag() & OC::RequestHandlerFlag::ObserverFlag))
265             {
266                 std::cout << "Provider : Income Observe : " << std::endl;
267                 setObserver(request, type);
268                 return OC_EH_OK;
269             }
270
271             auto pResponse = getResponse(request, type);
272             if (pResponse == nullptr)
273             {
274                 return OC_EH_ERROR;
275             }
276
277             try
278             {
279                 OC::OCPlatform::sendResponse(pResponse);
280             }
281             catch (std::exception &e)
282             {
283                 return OC_EH_ERROR;
284             }
285
286             return OC_EH_OK;
287         }
288
289     public:
290
291         void setAccepter(int accepter)
292         {
293             m_accepter = accepter;
294         }
295
296         void notifyMessage()
297         {
298             std::cout << "Provider : notify~" << std::endl;
299             OC::OCPlatform::notifyAllObservers(m_messageHandle);
300         }
301
302         void notifyMessage(const uint64_t &id, const std::string &title, const std::string &content)
303         {
304             setMessage(id, title, content);
305             notifyMessage();
306         }
307
308         void sendRead(const uint64_t &id)
309         {
310             std::string providerId = "123456789012345678901234567890123456";
311             m_syncRep.setValue<int>("x.org.iotivity.ns.messageid", id);
312             m_syncRep.setValue("x.org.iotivity.ns.state", (int)1);
313             m_syncRep.setValue("x.org.iotivity.ns.providerid", providerId);
314             OC::OCPlatform::notifyAllObservers(m_syncHandle);
315         }
316         void sendDismiss(const uint64_t &id)
317         {
318             std::string providerId = "123456789012345678901234567890123456";
319             m_syncRep.setValue<int>("x.org.iotivity.ns.messageid", id);
320             m_syncRep.setValue("x.org.iotivity.ns.state", (int)2);
321             m_syncRep.setValue("x.org.iotivity.ns.providerid", providerId);
322             OC::OCPlatform::notifyAllObservers(m_syncHandle);
323         }
324
325         void setMessage(const uint64_t &id, const std::string &title, const std::string &content)
326         {
327             std::string providerId = "123456789012345678901234567890123456";
328             m_messageRep.setValue<int>("x.org.iotivity.ns.messageid", id);
329             m_messageRep.setValue("x.org.iotivity.ns.title", title);
330             m_messageRep.setValue("x.org.iotivity.ns.contenttext", content);
331             m_messageRep.setValue("x.org.iotivity.ns.providerid", providerId);
332         }
333
334         void setTopics(const NS_TopicList &topics)
335         {
336             bool isChanged = false;
337             std::for_each (topics.begin(), topics.end(),
338                            [this, & isChanged](const std::string & topic)
339             {
340                 auto found = std::find(
341                                  this->m_topicList.begin(), this->m_topicList.end(), topic);
342                 if (found == this->m_topicList.end())
343                 {
344                     this->m_topicList.push_back(topic);
345                     isChanged = true;
346                 }
347             });
348
349             if (isChanged)
350             {
351                 this->notifyMessage((uint64_t)messageType::NS_TOPIC, "", "");
352             }
353         }
354
355         NS_TopicList getTopics() const
356         {
357             return m_topicList;
358         }
359
360         void updateTopicState(const NS_TopicStateList &allowedTopics)
361         {
362             std::for_each (allowedTopics.begin(), allowedTopics.end(),
363                            [this](const NS_TopicState & allowedTopic)
364             {
365                 auto found = this->m_allowedTopicList.find(allowedTopic.first);
366                 if (found != this->m_allowedTopicList.end())
367                 {
368                     found->second = allowedTopic.second;
369                 }
370             });
371         }
372
373         NS_TopicStateList getTopicAllowState() const
374         {
375             return m_allowedTopicList;
376         }
377
378         void deleteNotificationResource()
379         {
380             OC::OCPlatform::unregisterResource(m_notificationHandle);
381             OC::OCPlatform::unregisterResource(m_messageHandle);
382             OC::OCPlatform::unregisterResource(m_syncHandle);
383             OC::OCPlatform::unregisterResource(m_topicHandle);
384             m_allowedTopicList.clear();
385             m_topicList.clear();
386         }
387
388         void createNotificationResource()
389         {
390             createNotificationResource(m_notificationUri);
391         }
392
393         void createNotificationResource(const std::string &uri)
394         {
395             if (m_notificationUri != uri)
396             {
397                 m_notificationUri = uri;
398             }
399
400             OC::OCPlatform::startPresence(30);
401
402             std::string notificationUri = m_notificationUri;
403             std::string resourceTypeName = "x.org.iotivity.notification.topic";
404             std::string resourceInterface = OC::DEFAULT_INTERFACE;
405
406             uint8_t resourceProperty = OC_OBSERVABLE;
407             std::string childUri = uri + m_topicUri;
408             try
409             {
410                 OC::OCPlatform::registerResource(
411                     m_topicHandle, childUri,
412                     resourceTypeName, resourceInterface,
413                     std::bind(& NSProviderSimulator::entityHandler, this,
414                               std::placeholders::_1, requestType::NS_TOPIC),
415                     resourceProperty);
416             }
417             catch (std::exception &e)
418             {
419                 std::cout << e.what() << std::endl;
420             }
421
422             //resourceProperty |= OC_OBSERVABLE;
423             resourceTypeName = "x.org.iotivity.notification.message";
424             childUri = uri + m_messageUri;
425             try
426             {
427                 OC::OCPlatform::registerResource(
428                     m_messageHandle, childUri,
429                     resourceTypeName, resourceInterface,
430                     std::bind(& NSProviderSimulator::entityHandler, this,
431                               std::placeholders::_1, requestType::NS_MESSAGE),
432                     resourceProperty);
433             }
434             catch (std::exception &e)
435             {
436                 std::cout << e.what() << std::endl;
437             }
438
439             resourceTypeName = "x.org.iotivity.notification.sync";
440             childUri = uri + m_syncUri;
441             try
442             {
443                 OC::OCPlatform::registerResource(
444                     m_syncHandle, childUri,
445                     resourceTypeName, resourceInterface,
446                     std::bind(& NSProviderSimulator::entityHandler, this,
447                               std::placeholders::_1, requestType::NS_SYNC),
448                     resourceProperty);
449             }
450             catch (std::exception &e)
451             {
452                 std::cout << e.what() << std::endl;
453             }
454
455             resourceProperty |= OC_DISCOVERABLE;
456             resourceTypeName = "x.org.iotivity.notification";
457             try
458             {
459                 OC::OCPlatform::registerResource(
460                     m_notificationHandle, notificationUri,
461                     resourceTypeName, resourceInterface,
462                     std::bind(& NSProviderSimulator::entityHandler, this,
463                               std::placeholders::_1, requestType::NS_NOTIFICATION),
464                     resourceProperty);
465             }
466             catch (std::exception &e)
467             {
468                 std::cout << e.what() << std::endl;
469             }
470         }
471 };
472
473 #endif /* _NS_PROVIDER_SERVICE_SIMULATOR_H_ */