Merge branch 'master' into notification-service
[platform/upstream/iotivity.git] / service / notification / unittest / NSConsumerTest.cpp
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 #include <gtest/gtest.h>
22 #include <HippoMocks/hippomocks.h>
23 #include <atomic>
24 #include <functional>
25 #include <condition_variable>
26 #include <mutex>
27 #include <chrono>
28
29 #include "ocstack.h"
30
31 #include "NSCommon.h"
32 #include "NSConsumerInterface.h"
33
34 #include "NSProviderSimulator.h"
35
36 namespace
37 {
38     NSProviderSimulator g_providerSimul;
39     NSProvider * g_provider;
40
41     std::atomic_bool g_isStartedStack(false);
42
43     std::chrono::milliseconds g_waitForResponse(500);
44
45     std::condition_variable responseCon;
46     std::mutex mutexForCondition;
47
48     enum class NSSelector
49     {
50         NS_SELECTION_CONSUMER = 0,
51         NS_SELECTION_PROVIDER = 1
52     };
53
54     NSConsumerConfig cfg;
55 }
56
57 class TestWithMock: public testing::Test
58 {
59 public:
60     MockRepository mocks;
61
62 protected:
63     virtual ~TestWithMock() noexcept(noexcept(std::declval<Test>().~Test()))
64     {
65
66     }
67
68     virtual void TearDown()
69     {
70         try
71         {
72             mocks.VerifyAll();
73         }
74         catch (...)
75         {
76             mocks.reset();
77             throw;
78         }
79     }
80 };
81
82 class NotificationConsumerTest : public TestWithMock
83 {
84 public:
85     NotificationConsumerTest() = default;
86     ~NotificationConsumerTest() = default;
87
88     static void NSNotificationReceivedCallbackEmpty(NSMessage *)
89     {
90         std::cout << __func__ << std::endl;
91     }
92
93     static void NSSyncCallbackEmpty(NSSyncInfo *)
94     {
95         std::cout << __func__ << std::endl;
96     }
97
98     static void NSFoundResourceEmpty(std::shared_ptr< OC::OCResource >)
99     {
100         std::cout << __func__ << std::endl;
101     }
102
103     static void NSProviderChangedCallback(NSProvider *,  NSProviderState)
104     {
105         std::cout << __func__ << std::endl;
106     }
107
108 protected:
109
110     void SetUp()
111     {
112         TestWithMock::SetUp();
113
114         if (g_isStartedStack == false)
115         {
116             OC::PlatformConfig occfg
117             {
118                 OC::ServiceType::InProc,
119                 OC::ModeType::Both,
120                 "0.0.0.0",
121                 0,
122                 OC::QualityOfService::LowQos
123             };
124             OC::OCPlatform::Configure(occfg);
125
126             try
127             {
128                 OC::OCPlatform::stopPresence();
129             }
130             catch (...)
131             {
132
133             }
134
135             g_isStartedStack = true;
136
137             cfg.changedCb = NSProviderChangedCallback;
138             cfg.messageCb = NSNotificationReceivedCallbackEmpty;
139             cfg.syncInfoCb = NSSyncCallbackEmpty;
140         }
141
142     }
143
144     void TearDown()
145     {
146         TestWithMock::TearDown();
147     }
148
149 };
150
151 TEST_F(NotificationConsumerTest, StartConsumerPositive)
152 {
153     EXPECT_EQ(NS_OK, NSStartConsumer(cfg));
154     std::unique_lock< std::mutex > lock{ mutexForCondition };
155     responseCon.wait_for(lock, g_waitForResponse);
156 }
157
158 TEST_F(NotificationConsumerTest, StopConsumerPositive)
159 {
160     EXPECT_EQ(NSStopConsumer(), NS_OK);
161 }
162
163 TEST_F(NotificationConsumerTest, DiscoverProviderWithNonAccepterWhenStartedConsumerFirst)
164 {
165     mocks.ExpectCallFunc(NSProviderChangedCallback).Do(
166             [this](NSProvider *, NSProviderState)
167             {
168                 std::cout << "Call Discovered" << std::endl;
169                 responseCon.notify_all();
170             });
171
172     NSStartConsumer(cfg);
173
174     g_providerSimul.setAccepter((int)NSSelector::NS_SELECTION_CONSUMER);
175     g_providerSimul.createNotificationResource();
176
177     std::unique_lock< std::mutex > lock{ mutexForCondition };
178     responseCon.wait_for(lock, g_waitForResponse);
179
180     NSStopConsumer();
181     g_providerSimul.deleteNotificationResource();
182 }
183
184 TEST_F(NotificationConsumerTest, DiscoverProviderWithNonAccepterWhenStartedConsumerAfter)
185 {
186     g_providerSimul.setAccepter((int)NSSelector::NS_SELECTION_CONSUMER);
187     g_providerSimul.createNotificationResource();
188     {
189         std::unique_lock< std::mutex > lock{ mutexForCondition };
190         responseCon.wait_for(lock, g_waitForResponse);
191     }
192
193     mocks.ExpectCallFunc(NSProviderChangedCallback).Do(
194             [this](NSProvider * provider, NSProviderState)
195             {
196                 std::cout << "Call Discovered" << std::endl;
197                 g_provider = provider;
198                 responseCon.notify_all();
199             });
200
201     NSStartConsumer(cfg);
202
203     std::unique_lock< std::mutex > lock{ mutexForCondition };
204     responseCon.wait_for(lock, g_waitForResponse);
205
206 }
207
208 TEST_F(NotificationConsumerTest, DiscoverProviderWithNonAccepterWhenRescan)
209 {
210     g_providerSimul.setAccepter((int)NSSelector::NS_SELECTION_CONSUMER);
211     mocks.ExpectCallFunc(NSProviderChangedCallback).Do(
212             [this](NSProvider * provider, NSProviderState)
213             {
214                 std::cout << "Call Discovered" << std::endl;
215                 g_provider = provider;
216                 std::cout << g_provider->providerId << std::endl;
217                 responseCon.notify_all();
218             });
219
220     NSRescanProvider();
221
222     std::unique_lock< std::mutex > lock{ mutexForCondition };
223     responseCon.wait_for(lock, g_waitForResponse);
224
225 //    NSStopConsumer();
226 }
227
228 TEST_F(NotificationConsumerTest, ExpectSubscribeSuccess)
229 {
230 //    mocks.ExpectCallFunc(NSSubscriptionAcceptedCallback).Do(
231 //            [](NSProvider * )
232 //            {
233 //                std::cout << "Income Accepted subscription : " << std::endl;
234 //            });
235
236     NSResult ret = NSSubscribe(g_provider->providerId);
237     std::unique_lock< std::mutex > lock{ mutexForCondition };
238     responseCon.wait_for(lock, g_waitForResponse);
239
240     EXPECT_EQ(NS_OK, ret);
241 }
242
243 TEST_F(NotificationConsumerTest, ExpectReceiveNotification)
244 {
245     uint64_t id = 10;
246     std::string title = "title";
247     std::string msg = "msg";
248
249     mocks.ExpectCallFunc(NSNotificationReceivedCallbackEmpty).Do(
250             [](NSMessage * message)
251             {
252                 std::cout << "Income Notification : " << message->messageId << std::endl;
253             });
254
255     g_providerSimul.notifyMessage(id, title, msg);
256
257     std::unique_lock< std::mutex > lock{ mutexForCondition };
258     responseCon.wait_for(lock, g_waitForResponse);
259
260     NSStopConsumer();
261 }
262
263 TEST_F(NotificationConsumerTest, ExpectReceiveNotificationWithAccepterisProvider)
264 {
265     uint64_t id = 11;
266     std::string title = "title";
267     std::string msg = "msg";
268
269     g_providerSimul.setAccepter((int)NSSelector::NS_SELECTION_PROVIDER);
270
271     NSStartConsumer(cfg);
272     {
273         std::unique_lock< std::mutex > lock{ mutexForCondition };
274         responseCon.wait_for(lock, g_waitForResponse);
275     }
276
277     mocks.ExpectCallFunc(NSNotificationReceivedCallbackEmpty).Do(
278             [](NSMessage * message)
279             {
280                 std::cout << "Income Notification : " << message->messageId << std::endl;
281             });
282
283     g_providerSimul.notifyMessage(id, title, msg);
284
285     std::unique_lock< std::mutex > lock{ mutexForCondition };
286     responseCon.wait_for(lock, g_waitForResponse);
287
288 //    g_providerSimul.deleteNotificationResource();
289 //    NSStopConsumer();
290 }
291
292 TEST_F(NotificationConsumerTest, ExpectCallbackReadCheckWhenProviderNotifySync)
293 {
294     uint64_t id = 12;
295     std::string title = "title";
296     std::string msg = "msg";
297
298     NSSyncType type = NS_SYNC_DELETED;
299
300     mocks.OnCallFunc(NSNotificationReceivedCallbackEmpty).Do(
301             [](NSMessage * message)
302             {
303                 std::cout << "Income Notification : " << message->messageId << std::endl;
304             });
305
306     mocks.ExpectCallFunc(NSSyncCallbackEmpty).Do(
307             [& type](NSSyncInfo * sync)
308             {
309                 std::cout << "Income SyncInfo : " << sync->messageId
310                         << ", State : " << sync->state << std::endl;
311                 type = sync->state;
312
313             });
314
315     g_providerSimul.notifyMessage(id, title, msg);
316     {
317         std::unique_lock< std::mutex > lock{ mutexForCondition };
318         responseCon.wait_for(lock, g_waitForResponse);
319     }
320
321     g_providerSimul.sendRead(id);
322     {
323         std::unique_lock< std::mutex > lock{ mutexForCondition };
324         responseCon.wait_for(lock, g_waitForResponse);
325     }
326
327 //    g_providerSimul.deleteNotificationResource();
328 //    NSStopConsumer();
329
330     EXPECT_EQ(NS_SYNC_READ, type);
331 }
332
333 TEST_F(NotificationConsumerTest, ExpectCallbackDismissCheckWhenProviderNotifySync)
334 {
335     uint64_t id = 13;
336     std::string title = "title";
337     std::string msg = "msg";
338
339     NSSyncType type = NS_SYNC_READ;
340
341     mocks.OnCallFunc(NSNotificationReceivedCallbackEmpty).Do(
342             [](NSMessage * message)
343             {
344                 std::cout << "Income Notification : " << message->messageId << std::endl;
345             });
346
347     mocks.ExpectCallFunc(NSSyncCallbackEmpty).Do(
348             [& type](NSSyncInfo * sync)
349             {
350                 std::cout << "Income Notification : " << sync->messageId
351                         << ", State : " << sync->state << std::endl;
352                 type = sync->state;
353
354             });
355
356     g_providerSimul.notifyMessage(id, title, msg);
357     {
358         std::unique_lock< std::mutex > lock{ mutexForCondition };
359         responseCon.wait_for(lock, g_waitForResponse);
360     }
361
362     g_providerSimul.sendDismiss(id);
363     {
364         std::unique_lock< std::mutex > lock{ mutexForCondition };
365         responseCon.wait_for(lock, g_waitForResponse);
366     }
367
368 //    g_providerSimul.deleteNotificationResource();
369 //    NSStopConsumer();
370
371     EXPECT_EQ(NS_SYNC_DELETED, type);
372 }
373
374 TEST_F(NotificationConsumerTest, ExpectCallbackReadCheckWhenConsumerPostSync)
375 {
376     uint64_t id = 14;
377     std::string title = "title";
378     std::string msg = "msg";
379
380     NSSyncType type = NS_SYNC_DELETED;
381
382     mocks.OnCallFunc(NSNotificationReceivedCallbackEmpty).Do(
383             [](NSMessage * message)
384             {
385                 std::cout << "Income Notification : " << message->messageId << std::endl;
386                 NSConsumerSendSyncInfo(message->providerId, message->messageId, NS_SYNC_READ);
387                 std::unique_lock< std::mutex > lock{ mutexForCondition };
388                 responseCon.wait_for(lock, g_waitForResponse);
389             });
390
391     mocks.ExpectCallFunc(NSSyncCallbackEmpty).Do(
392             [& type](NSSyncInfo * sync)
393             {
394                 std::cout << "Income Notification : " << sync->messageId
395                         << ", State : " << sync->state << std::endl;
396                 type = sync->state;
397
398             });
399
400     g_providerSimul.notifyMessage(id, title, msg);
401     {
402         std::unique_lock< std::mutex > lock{ mutexForCondition };
403         responseCon.wait_for(lock, g_waitForResponse);
404     }
405
406 //    g_providerSimul.deleteNotificationResource();
407 //    NSStopConsumer();
408
409     EXPECT_EQ(NS_SYNC_READ, type);
410 }
411
412 TEST_F(NotificationConsumerTest, ExpectCallbackDismissCheckWhenConsumerPostSync)
413 {
414     uint64_t id = 15;
415     std::string title = "title";
416     std::string msg = "msg";
417
418     NSSyncType type = NS_SYNC_READ;
419
420     mocks.OnCallFunc(NSNotificationReceivedCallbackEmpty).Do(
421             [](NSMessage * message)
422             {
423                 std::cout << "Income Notification : " << message->messageId << std::endl;
424                 NSConsumerSendSyncInfo(message->providerId, message->messageId, NS_SYNC_DELETED);
425                 std::unique_lock< std::mutex > lock{ mutexForCondition };
426                 responseCon.wait_for(lock, g_waitForResponse);
427             });
428
429     mocks.ExpectCallFunc(NSSyncCallbackEmpty).Do(
430             [& type](NSSyncInfo * sync)
431             {
432                 std::cout << "Income Notification : " << sync->messageId
433                         << ", State : " << sync->state << std::endl;
434                 type = sync->state;
435
436             });
437
438     g_providerSimul.notifyMessage(id, title, msg);
439     {
440         std::unique_lock< std::mutex > lock{ mutexForCondition };
441         responseCon.wait_for(lock, g_waitForResponse);
442     }
443
444     g_providerSimul.deleteNotificationResource();
445     NSStopConsumer();
446
447     EXPECT_EQ(NS_SYNC_DELETED, type);
448 }
449
450 //TEST_F(NotificationConsumerTest, ExpectUnsubscribeSuccess)
451 //{
452 //    NSResult ret = NSUnsubscribe(g_provider->providerId);
453 //    std::unique_lock< std::mutex > lock{ mutexForCondition };
454 //    responseCon.wait_for(lock, g_waitForResponse);
455 //
456 //    g_providerSimul.deleteNotificationResource();
457 //    NSStopConsumer();
458 //
459 //    EXPECT_EQ(NS_OK, ret);
460 //}