Add message queue, group&invite sample for cloud
authorJee Hyeok Kim <jihyeok13.kim@samsung.com>
Mon, 29 Aug 2016 03:56:35 +0000 (12:56 +0900)
committerJee Hyeok Kim <jihyeok13.kim@samsung.com>
Thu, 1 Sep 2016 01:25:27 +0000 (01:25 +0000)
1. Add message queue clients
2. Add group & invite samples
3. cleanup existing clients

Change-Id: Ibe107a979e3cee253c4a74bbbc991da934371bc2
Signed-off-by: Jee Hyeok Kim <jihyeok13.kim@samsung.com>
Reviewed-on: https://gerrit.iotivity.org/gerrit/11099
Tested-by: jenkins-iotivity <jenkins-iotivity@opendaylight.org>
cloud/samples/client/README
cloud/samples/client/SConscript
cloud/samples/client/airconditioner/aircon_controlee.cpp
cloud/samples/client/airconditioner/aircon_controller.cpp
cloud/samples/client/group_invite/group_invite.cpp [new file with mode: 0644]
cloud/samples/client/messagequeue/mq_publisher.cpp [new file with mode: 0644]
cloud/samples/client/messagequeue/mq_subscriber.cpp [new file with mode: 0644]

index 734609f..50f9380 100644 (file)
@@ -1,14 +1,14 @@
-To build cloud client sample, add WITH_TCP, TARGET_TRANSPORT=IP and WITH_CLOUD option to build command
+To build cloud client samples, add WITH_TCP, TARGET_TRANSPORT=IP, WITH_CLOUD and WITH_MQ option to build command line
 
-ex) scons WITH_TCP=yes TARGET_TRANSPORT=IP WITH_CLOUD=yes
+ex) scons WITH_TCP=yes TARGET_TRANSPORT=IP WITH_CLOUD=yes WITH_MQ=PUB,SUB
 
-Cloud client runs using CoAP over TCP transport. So you should add WITH_TCP option.
+Cloud clients runs over CoAP over TCP transport. So you should declare WITH_TCP option.
 
-Once you get sample which file name is 'aircon_controlee' and 'aircon_controller', you need 'Auth Code' to register resources on cloud with account scenario.
+Once you get samples which file name is 'aircon_controlee' and 'aircon_controller', you need 'Auth Code' to register resources on cloud with account scenario.
 
 Cloud stack has sample github oauth2 adaptor.
 
-So you can instantly test sample using 'Auth Code'.
+So you can instantly test samples using 'Auth Code'.
 
 Paste below URL to your browser
 
index d3a7e37..23cfaef 100644 (file)
@@ -69,4 +69,35 @@ cc_sample_app_env.Program('aircon_controlee', aircon_controlee_src)
 aircon_controller_src = [
         'airconditioner/aircon_controller.cpp'
         ]
-cc_sample_app_env.Program('aircon_controller', aircon_controller_src)
\ No newline at end of file
+cc_sample_app_env.Program('aircon_controller', aircon_controller_src)
+
+
+######################################################################
+# Samples for message queue
+######################################################################
+mqOption = env.get('WITH_MQ')
+if mqOption[0] is not 'OFF':
+       cc_sample_app_env.AppendUnique(CPPDEFINES = ['WITH_MQ'])
+       if set(['PUB']) == set(mqOption):
+               cc_sample_app_env.AppendUnique(CPPDEFINES = ['MQ_PUBLISHER'])
+               mq_publisher_src = ['messagequeue/mq_publisher.cpp']
+               cc_sample_app_env.Program('mq_publisher', mq_publisher_src)
+       elif set(['SUB']) == set(mqOption):
+               cc_sample_app_env.AppendUnique(CPPDEFINES = ['MQ_SUBSCRIBER'])
+               mq_subscriber_src = ['messagequeue/mq_subscriber.cpp']
+               cc_sample_app_env.Program('mq_subscriber', mq_subscriber_src)
+       else:
+               cc_sample_app_env.AppendUnique(CPPDEFINES = ['MQ_PUBLISHER'])
+               mq_publisher_src = ['messagequeue/mq_publisher.cpp']
+               cc_sample_app_env.Program('mq_publisher', mq_publisher_src)
+               cc_sample_app_env.AppendUnique(CPPDEFINES = ['MQ_SUBSCRIBER'])
+               mq_subscriber_src = ['messagequeue/mq_subscriber.cpp']
+               cc_sample_app_env.Program('mq_subscriber', mq_subscriber_src)
+
+######################################################################
+# Samples for group and invite
+######################################################################
+group_invite_src = [
+        'group_invite/group_invite.cpp'
+        ]
+cc_sample_app_env.Program('group_invite_sample', group_invite_src)
\ No newline at end of file
index dec0b90..19bf82c 100644 (file)
@@ -5,7 +5,6 @@
 #include <map>
 #include <vector>
 #include <string>
-#include <pthread.h>
 #include <unistd.h>
 
 #include "ocstack.h"
@@ -15,8 +14,6 @@
 #include <OCApi.h>
 #include <OCPlatform.h>
 
-#define DEFAULT_CONTEXT_VALUE 0x99
-
 using namespace OC;
 using namespace std;
 
@@ -438,50 +435,11 @@ void onPublish(const OCRepresentation &, const int &eCode)
     g_callbackLock.notify_all();
 }
 
-void printRepresentation(OCRepPayloadValue *value)
+void printRepresentation(OCRepresentation rep)
 {
-    while (value)
+    for (auto itr = rep.begin(); itr != rep.end(); ++itr)
     {
-        std::cout << "Key: " << value->name;
-        switch (value->type)
-        {
-            case OCREP_PROP_NULL:
-                std::cout << " Value: None" << std::endl;
-                break;
-            case OCREP_PROP_INT:
-                std::cout << " Value: " << value->i << std::endl;
-                break;
-            case OCREP_PROP_DOUBLE:
-                std::cout << " Value: " << value->d << std::endl;
-                break;
-            case OCREP_PROP_BOOL:
-                std::cout << " Value: " << value->b << std::endl;
-                break;
-            case OCREP_PROP_STRING:
-                std::cout << " Value: " << value->str << std::endl;
-                break;
-            case OCREP_PROP_BYTE_STRING:
-                std::cout << " Value: Byte String" << std::endl;
-                break;
-            case OCREP_PROP_OBJECT:
-                std::cout << " Value: Object" << std::endl;
-                break;
-            case OCREP_PROP_ARRAY:
-                std::cout << " Value: Array" << std::endl;
-                break;
-        }
-
-        if (strcmp(value->name, "accesstoken") == 0)
-        {
-            g_accesstoken = value->str;
-        }
-
-        if (strcmp(value->name, "uid") == 0)
-        {
-            g_uid = value->str;
-        }
-
-        value = value->next;
+        cout << "\t" << itr->attrname() << ":\t" << itr->getValueToString() << endl;
     }
 }
 
@@ -492,7 +450,14 @@ void handleLoginoutCB(const HeaderOptions &,
 
     if (rep.getPayload() != NULL)
     {
-        printRepresentation(rep.getPayload()->values);
+        printRepresentation(rep);
+    }
+
+    if (ecode == 4)
+    {
+        g_accesstoken = rep.getValueToString("accesstoken");
+
+        g_uid = rep.getValueToString("uid");
     }
 
     g_callbackLock.notify_all();
@@ -500,7 +465,7 @@ void handleLoginoutCB(const HeaderOptions &,
 
 static FILE *client_open(const char * /*path*/, const char *mode)
 {
-    return fopen("./resource_server.dat", mode);
+    return fopen("./aircon_controlee.dat", mode);
 }
 
 int main(int argc, char *argv[])
index 6dc5e02..2aaae0f 100644 (file)
@@ -5,7 +5,6 @@
 #include <map>
 #include <vector>
 #include <string>
-#include <pthread.h>
 #include <unistd.h>
 
 #include "ocstack.h"
@@ -14,8 +13,6 @@
 #include <OCApi.h>
 #include <OCPlatform.h>
 
-#define DEFAULT_CONTEXT_VALUE 0x99
-
 #define maxSequenceNumber 0xFFFFFF
 
 using namespace OC;
@@ -29,50 +26,11 @@ std::string         g_accesstoken;
 string              g_host;
 OC::OCResource::Ptr g_binaryswitchResource;
 
-void printRepresentation(OCRepPayloadValue *value)
+void printRepresentation(OCRepresentation rep)
 {
-    while (value)
+    for (auto itr = rep.begin(); itr != rep.end(); ++itr)
     {
-        std::cout << "Key: " << value->name;
-        switch (value->type)
-        {
-            case OCREP_PROP_NULL:
-                std::cout << " Value: None" << std::endl;
-                break;
-            case OCREP_PROP_INT:
-                std::cout << " Value: " << value->i << std::endl;
-                break;
-            case OCREP_PROP_DOUBLE:
-                std::cout << " Value: " << value->d << std::endl;
-                break;
-            case OCREP_PROP_BOOL:
-                std::cout << " Value: " << value->b << std::endl;
-                break;
-            case OCREP_PROP_STRING:
-                std::cout << " Value: " << value->str << std::endl;
-                break;
-            case OCREP_PROP_BYTE_STRING:
-                std::cout << " Value: Byte String" << std::endl;
-                break;
-            case OCREP_PROP_OBJECT:
-                std::cout << " Value: Object" << std::endl;
-                break;
-            case OCREP_PROP_ARRAY:
-                std::cout << " Value: Array" << std::endl;
-                break;
-        }
-
-        if (strcmp(value->name, "accesstoken") == 0)
-        {
-            g_accesstoken = value->str;
-        }
-
-        if (strcmp(value->name, "uid") == 0)
-        {
-            g_uid = value->str;
-        }
-
-        value = value->next;
+        cout << "\t" << itr->attrname() << ":\t" << itr->getValueToString() << endl;
     }
 }
 
@@ -83,13 +41,20 @@ void handleLoginoutCB(const HeaderOptions &,
 
     if (rep.getPayload() != NULL)
     {
-        printRepresentation(rep.getPayload()->values);
+        printRepresentation(rep);
+    }
+
+    if (ecode == 4)
+    {
+        g_accesstoken = rep.getValueToString("accesstoken");
+
+        g_uid = rep.getValueToString("uid");
     }
 
     g_callbackLock.notify_all();
 }
 
-void printRepresentation(const OCRepresentation &rep)
+void printResource(const OCRepresentation &rep)
 {
     cout << "URI: " << rep.getUri() << endl;
 
@@ -110,7 +75,7 @@ void printRepresentation(const OCRepresentation &rep)
     for (auto it = children.begin();
          it != children.end(); it++)
     {
-        printRepresentation(*it);
+        printResource(*it);
     }
 }
 
@@ -127,7 +92,7 @@ void onObserve(const HeaderOptions /*headerOptions*/, const OCRepresentation &re
             }
 
             cout << "OBSERVE RESULT:" << endl;
-            printRepresentation(rep);
+            printResource(rep);
         }
         else
         {
@@ -152,7 +117,7 @@ void onPut(const HeaderOptions & /*headerOptions*/, const OCRepresentation &rep,
 {
     cout << "PUT response: " << eCode << endl;
 
-    printRepresentation(rep);
+    printResource(rep);
 }
 
 void turnOnOffSwitch(bool toTurn)
@@ -169,7 +134,7 @@ void getCollectionResource(const HeaderOptions &,
 {
     cout << "Resource get: " << ecode << endl;
 
-    printRepresentation(rep);
+    printResource(rep);
 
     vector<OCRepresentation> children = rep.getChildren();
 
@@ -238,6 +203,14 @@ void foundDevice(shared_ptr<OC::OCResource> resource)
             OCPlatform::findResource(g_host, searchQuery,
                                      static_cast<OCConnectivityType>(CT_ADAPTER_TCP | CT_IP_USE_V4),
                                      &foundAirconditionerResource);
+
+            OCPlatform::OCPresenceHandle    handle;
+            if (OCPlatform::subscribeDevicePresence(handle, g_host, { resource->sid() },
+                                                    static_cast<OCConnectivityType>
+                                                    (CT_ADAPTER_TCP | CT_IP_USE_V4), &onObserve) != OC_STACK_OK)
+            {
+                cout << "Device presence failed" << endl;
+            }
         }
     }
 }
@@ -249,7 +222,7 @@ void presenceDevice(OCStackResult , const unsigned int i, const std::string &str
 
 static FILE *client_open(const char * /*path*/, const char *mode)
 {
-    return fopen("./resource_controller.dat", mode);
+    return fopen("./aircon_controller.dat", mode);
 }
 
 int main(int argc, char *argv[])
diff --git a/cloud/samples/client/group_invite/group_invite.cpp b/cloud/samples/client/group_invite/group_invite.cpp
new file mode 100644 (file)
index 0000000..c836023
--- /dev/null
@@ -0,0 +1,369 @@
+/* ****************************************************************
+*
+* Copyright 2016 Samsung Electronics All Rights Reserved.
+*
+*
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+*      http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*
+******************************************************************/
+
+#include <memory>
+#include <iostream>
+#include <stdexcept>
+#include <condition_variable>
+#include <map>
+#include <vector>
+#include <string>
+#include <unistd.h>
+#include <stdio.h>
+
+#include "ocstack.h"
+#include "ocpayload.h"
+
+#include <OCApi.h>
+#include <OCPlatform.h>
+
+using namespace std;
+using namespace OC;
+
+#define maxSequenceNumber 0xFFFFFF
+
+void printRepresentation(OCRepresentation rep)
+{
+    for (auto itr = rep.begin(); itr != rep.end(); ++itr)
+    {
+        cout << "\t" << itr->attrname() << ":\t" << itr->getValueToString() << endl;
+    }
+}
+
+void onSearchUser(const HeaderOptions & /*headerOptions*/,
+                  const OCRepresentation &rep, const int eCode)
+{
+    if (eCode == OC_STACK_OK || eCode == OC_STACK_RESOURCE_CHANGED)
+    {
+        cout << "\tSearchUser request was successful" << endl;
+
+        std::vector<OCRepresentation> userList = rep.getValue<std::vector<OCRepresentation>>("ulist");
+
+        for (auto user : userList)
+        {
+            // Mandatory field
+            cout << "\tuid: " << user.getValue<string>("uid") << endl;
+
+            // Optional field
+            cout << "\tuinfo: " << endl;
+            OCRepresentation uinfo = user.getValue<OCRepresentation>("uinfo");
+            for (auto itr = uinfo.begin(); itr != uinfo.end(); ++itr)
+            {
+                cout << "\t\t" << itr->attrname() << ":\t" << itr->getValueToString() << endl;
+            }
+            cout << endl;
+        }
+    }
+    else
+    {
+        cout << "\tSearchUser Response error: " << eCode << endl;
+    }
+}
+
+//tmp callback
+void ocPost(const HeaderOptions & /*headerOptions*/,
+            const OCRepresentation &rep, const int eCode)
+{
+    if (eCode == OC_STACK_OK || eCode == OC_STACK_RESOURCE_CHANGED)
+    {
+        std::cout << "\tRequest was successful: " << eCode << std::endl;
+
+        printRepresentation(rep);
+    }
+    else
+    {
+        std::cout << "\tResponse error: " << eCode << std::endl;
+    }
+}
+
+void onObserve(const HeaderOptions /*headerOptions*/, const OCRepresentation &rep,
+               const int &eCode, const int &sequenceNumber)
+{
+    try
+    {
+        if (eCode == OC_STACK_OK && sequenceNumber != maxSequenceNumber + 1)
+        {
+            if (sequenceNumber == OC_OBSERVE_REGISTER)
+            {
+                cout << "Observe registration action is successful" << endl;
+            }
+
+            cout << "OBSERVE RESULT:" << endl;
+            printRepresentation(rep);
+        }
+        else
+        {
+            if (eCode == OC_STACK_OK)
+            {
+                std::cout << "Observe registration failed or de-registration action failed/succeeded" << std::endl;
+            }
+            else
+            {
+                cout << "onObserve Response error: " << eCode << endl;
+                exit(-1);
+            }
+        }
+    }
+    catch (exception &e)
+    {
+        cout << "Exception: " << e.what() << " in onObserve" << endl;
+    }
+}
+
+void onDelete(const HeaderOptions & /*headerOptions*/,
+              const int eCode)
+{
+    if (eCode == OC_STACK_OK || eCode == OC_STACK_RESOURCE_DELETED)
+    {
+        cout << "\tDelete was successful" << endl;
+    }
+    else
+    {
+        cout << "\tDelete Response error: " << eCode << endl;
+    }
+}
+
+std::condition_variable g_callbackLock;
+std::string             g_uid;
+std::string             g_accesstoken;
+
+void handleLoginoutCB(const HeaderOptions &,
+                      const OCRepresentation &rep, const int ecode)
+{
+    cout << "Auth response received code: " << ecode << endl;
+
+    if (rep.getPayload() != NULL)
+    {
+        printRepresentation(rep);
+    }
+
+    if (ecode == 4)
+    {
+        g_accesstoken = rep.getValueToString("accesstoken");
+
+        g_uid = rep.getValueToString("uid");
+    }
+
+    g_callbackLock.notify_all();
+}
+
+int main(int argc, char *argv[])
+{
+    if (argc != 4 && argc != 5)
+    {
+        cout << "Put \"[host-ipaddress:port] [authprovider] [authcode]\" for sign-up and sign-in"
+             << endl;
+        cout << "Put \"[host-ipaddress:port] [uid] [accessToken] 1\" for sign-in" <<
+             endl;
+        return 0;
+    }
+
+    PlatformConfig cfg
+    {
+        ServiceType::InProc,
+        ModeType::Both,
+        "0.0.0.0", // By setting to "0.0.0.0", it binds to all available interfaces
+        0,         // Uses randomly available port
+        QualityOfService::LowQos
+    };
+
+    OCPlatform::Configure(cfg);
+
+    OCStackResult result = OC_STACK_ERROR;
+
+    string host = "coap+tcp://";
+    host += argv[1];
+
+    OCAccountManager::Ptr accountMgr = OCPlatform::constructAccountManagerObject(host,
+                                       CT_ADAPTER_TCP);
+
+    mutex blocker;
+    unique_lock<std::mutex> lock(blocker);
+
+    if (argc == 5)
+    {
+        accountMgr->signIn(argv[2], argv[3], &handleLoginoutCB);
+        g_callbackLock.wait(lock);
+    }
+    else
+    {
+        accountMgr->signUp(argv[2], argv[3], &handleLoginoutCB);
+        g_callbackLock.wait(lock);
+        accountMgr->signIn(g_uid, g_accesstoken, &handleLoginoutCB);
+        g_callbackLock.wait(lock);
+    }
+
+    cout << "---Group & Invite sample---" << endl;
+    cout << "     1 - searchUser" << endl;
+    cout << "     2 - deleteDevice" << endl;
+    cout << "     3 - createGroup" << endl;
+    cout << "     4 - observeGroup" << endl;
+    cout << "     5 - getGroupList" << endl;
+    cout << "     6 - deleteGroup" << endl;
+    cout << "     7 - joinGroup" << endl;
+    cout << "     8 - addDeviceToGroup" << endl;
+    cout << "     9 - getGroupInfo" << endl;
+    cout << "    10 - leaveGroup" << endl;
+    cout << "    11 - deleteDeviceFromGroup" << endl;
+    cout << "    12 - observeInvitation" << endl;
+    cout << "    13 - sendInvitation" << endl;
+    cout << "    14 - cancelInvitation" << endl;
+    cout << "    15 - deleteInvitation" << endl;
+    cout << "    16 - cancelObserveGroup" << endl;
+    cout << "    17 - cancelObserveInvitation" << endl;
+    cout << "    18 - exit" << endl;
+
+    string cmd;
+    string cmd2;
+
+    while (true)
+    {
+        cin >> cmd;
+
+        QueryParamsMap query;
+        OCRepresentation rep;
+
+        switch (atoi(cmd.c_str()))
+        {
+            case 1:
+                cout << "Put userUUID to search:" << endl;
+                cin >> cmd;
+                result = accountMgr->searchUser(cmd, &onSearchUser);
+                break;
+
+            case 2:
+                cout << "PUT deviceID to delete:";
+                cin >> cmd;
+                result = accountMgr->deleteDevice(cmd, &onDelete);
+                break;
+
+            case 3:
+                result = accountMgr->createGroup(OC::AclGroupType::PUBLIC, &ocPost);
+                break;
+
+            case 4:
+                cout << "PUT groupId to observe:";
+                cin >> cmd;
+                result = accountMgr->observeGroup(cmd, &onObserve);
+                break;
+
+            case 5:
+                result = accountMgr->getGroupList(&ocPost);
+                break;
+
+            case 6:
+                cout << "PUT groupId to delete:";
+                cin >> cmd;
+                result = accountMgr->deleteGroup(cmd, &onDelete);
+                break;
+
+            case 7:
+                cout << "PUT groupId to join:";
+                cin >> cmd;
+                result = accountMgr->joinGroup(cmd, &ocPost);
+                break;
+
+            case 8:
+                cout << "PUT groupId to add device:";
+                cin >> cmd;
+                cout << "PUT deviceId to add to group:";
+                cin >> cmd2;
+                {
+                    std::vector<std::string> deviceIds;
+                    deviceIds.push_back(cmd2);
+                    result = accountMgr->addDeviceToGroup(cmd, deviceIds, &ocPost);
+                }
+                break;
+
+            case 9:
+                cout << "PUT groupId to get info:";
+                cin >> cmd;
+                result = accountMgr->getGroupInfo(cmd, &ocPost);
+                break;
+
+            case 10:
+                cout << "PUT groupId to leave:";
+                cin >> cmd;
+                result = accountMgr->leaveGroup(cmd, &onDelete);
+                break;
+
+            case 11:
+                cout << "PUT groupId to remove device:";
+                cin >> cmd;
+                cout << "PUT deviceId to remove from group:";
+                cin >> cmd2;
+                {
+                    std::vector<std::string> deviceIds;
+                    deviceIds.push_back(cmd2);
+                    result = accountMgr->deleteDeviceFromGroup(cmd, deviceIds, &onDelete);
+                }
+                break;
+
+            case 12:
+                result = accountMgr->observeInvitation(&onObserve);
+                break;
+
+            case 13:
+                cout << "PUT groupId to invite:";
+                cin >> cmd;
+                cout << "PUT userUUID to invite:";
+                cin >> cmd2;
+                result = accountMgr->sendInvitation(cmd, cmd2, &ocPost);
+                break;
+
+            case 14:
+                cout << "PUT groupId to cancel invitation:";
+                cin >> cmd;
+                cout << "PUT userUUID to cancel invitation:";
+                cin >> cmd2;
+                result = accountMgr->cancelInvitation(cmd, cmd2, &onDelete);
+                break;
+
+            case 15:
+                cout << "PUT groupId to delete invitation:";
+                cin >> cmd;
+                result = accountMgr->deleteInvitation(cmd, &onDelete);
+                break;
+
+            case 16:
+                cout << "PUT groupId to cancel observe:";
+                cin >> cmd;
+                result = accountMgr->cancelObserveGroup(cmd);
+                break;
+
+            case 17:
+                result = accountMgr->cancelObserveInvitation();
+                break;
+
+            //113 is q
+            case 18:
+                goto exit;
+                break;
+        }
+
+        if (result != OC_STACK_OK)
+        {
+            cout << "Error, return code: " << result << endl;
+        }
+    }
+
+exit:
+    return 0;
+}
\ No newline at end of file
diff --git a/cloud/samples/client/messagequeue/mq_publisher.cpp b/cloud/samples/client/messagequeue/mq_publisher.cpp
new file mode 100644 (file)
index 0000000..dbb558f
--- /dev/null
@@ -0,0 +1,250 @@
+//******************************************************************
+//
+// Copyright 2016 Samsung Electronics All Rights Reserved.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+///
+/// This sample provides the way to create cloud sample
+///
+#include <memory>
+#include <iostream>
+#include <stdexcept>
+#include <condition_variable>
+#include <map>
+#include <vector>
+#include <string>
+#include <unistd.h>
+#include <stdio.h>
+
+#include "ocstack.h"
+#include "ocpayload.h"
+
+#include <OCApi.h>
+#include <OCPlatform.h>
+
+using namespace OC;
+using namespace std;
+
+#define DEFAULT_MQ_BROKER_URI "/oic/ps"
+
+OC::OCResource::Ptr g_mqBrokerResource = nullptr;
+OC::OCResource::Ptr g_mqSelectedTopicResource = nullptr;
+
+vector<shared_ptr<OC::OCResource> > gTopicList;
+
+void printRepresentation(OCRepresentation rep)
+{
+    for (auto itr = rep.begin(); itr != rep.end(); ++itr)
+    {
+        cout << "\t" << itr->attrname() << ":\t" << itr->getValueToString() << endl;
+    }
+}
+
+////////////////////////////////////////Publisher Sample
+
+void createTopicCB(const int ecode, const std::string &originUri,
+                   std::shared_ptr<OC::OCResource> topic)
+{
+    std::cout << "Create topic response received, code: " << ecode << std::endl;
+
+    if (ecode == OCStackResult::OC_STACK_RESOURCE_CREATED)
+    {
+        std::cout << "Created topic : " << topic->uri() << std::endl;
+    }
+    else
+    {
+        std::cout << "Topic creation failed : " << originUri << std::endl;
+    }
+}
+
+void publishMessageCB(const HeaderOptions &, const OCRepresentation &, const int eCode)
+{
+    std::cout << "Publish message response received, code: " << eCode << std::endl;
+}
+
+void discoverTopicCB(const int ecode, const std::string &, std::shared_ptr<OC::OCResource> topic)
+{
+    cout << "Topic discovered code: " << ecode << endl;
+    gTopicList.push_back(topic);
+    cout << "Topic [" << gTopicList.size() - 1 << "] " << topic->uri() << " discovered" << endl;
+}
+////////////////////////////////////////End of Publisher Sample
+
+std::condition_variable g_callbackLock;
+std::string             g_uid;
+std::string             g_accesstoken;
+
+void handleLoginoutCB(const HeaderOptions &,
+                      const OCRepresentation &rep, const int ecode)
+{
+    cout << "Auth response received code: " << ecode << endl;
+
+    if (rep.getPayload() != NULL)
+    {
+        printRepresentation(rep);
+    }
+
+    if (ecode == 4)
+    {
+        g_accesstoken = rep.getValueToString("accesstoken");
+
+        g_uid = rep.getValueToString("uid");
+    }
+
+    g_callbackLock.notify_all();
+}
+
+static FILE *client_open(const char * /*path*/, const char *mode)
+{
+    return fopen("./mq_publisher.dat", mode);
+}
+
+int main(int argc, char *argv[])
+{
+    if (argc != 4 && argc != 5)
+    {
+        cout << "Put \"[host-ipaddress:port] [authprovider] [authcode]\" for sign-up and sign-in"
+             << endl;
+        cout << "Put \"[host-ipaddress:port] [uid] [accessToken] 1\" for sign-in" <<
+             endl;
+        return 0;
+    }
+
+    OCPersistentStorage ps{ client_open, fread, fwrite, fclose, unlink };
+
+    PlatformConfig cfg
+    {
+        ServiceType::InProc,
+        ModeType::Both,
+        "0.0.0.0", // By setting to "0.0.0.0", it binds to all available interfaces
+        0,         // Uses randomly available port
+        QualityOfService::LowQos,
+        &ps
+    };
+
+    OCPlatform::Configure(cfg);
+
+    OCStackResult result = OC_STACK_ERROR;
+
+    string host = "coap+tcp://";
+    host += argv[1];
+
+    OCAccountManager::Ptr accountMgr = OCPlatform::constructAccountManagerObject(host,
+                                       CT_ADAPTER_TCP);
+
+    mutex blocker;
+    unique_lock<std::mutex> lock(blocker);
+
+    if (argc == 5)
+    {
+        accountMgr->signIn(argv[2], argv[3], &handleLoginoutCB);
+        g_callbackLock.wait(lock);
+    }
+    else
+    {
+        accountMgr->signUp(argv[2], argv[3], &handleLoginoutCB);
+        g_callbackLock.wait(lock);
+        accountMgr->signIn(g_uid, g_accesstoken, &handleLoginoutCB);
+        g_callbackLock.wait(lock);
+    }
+
+    // MQ broker resource
+    g_mqBrokerResource = OCPlatform::constructResourceObject(host, DEFAULT_MQ_BROKER_URI,
+                         static_cast<OCConnectivityType>(CT_ADAPTER_TCP | CT_IP_USE_V4), false,
+    { string("oic.wk.ps") }, { string(DEFAULT_INTERFACE) });
+
+    cout << "===Message Queue publisher sample===" << endl;
+    cout << "PUT 0 to discover all topics" << endl;
+    cout << "PUT 1 to discover type based topics" << endl;
+    cout << "PUT 2 to select topic index for publishing data" << endl;
+    cout << "PUT 3 to publish data to selected topic" << endl;
+    cout << "PUT 4 to create topic" << endl;
+    cout << "PUT 5 to create type based topic" << endl;
+
+    string cmd;
+
+    while (true)
+    {
+        cin >> cmd;
+
+        QueryParamsMap query;
+        OCRepresentation rep;
+        string      topicType;
+
+        switch (cmd[0])
+        {
+            case '0':
+                gTopicList.clear();
+                cout << "Discovering topics" << endl;
+                result = g_mqBrokerResource->discoveryMQTopics(query, &discoverTopicCB, QualityOfService::LowQos);
+                break;
+
+            case '1':
+                gTopicList.clear();
+                cout << "Put topic type to discover: ";
+                cin >> cmd;
+                query["rt"] = cmd;
+                result = g_mqBrokerResource->discoveryMQTopics(query, &discoverTopicCB, QualityOfService::LowQos);
+                break;
+
+            case '2':
+                cout << "Put discovered topic index to select: ";
+                cin >> cmd;
+                g_mqSelectedTopicResource = gTopicList[atoi(cmd.c_str())];
+                cout << g_mqSelectedTopicResource->uri() << " selected" << endl;
+                break;
+
+            case '3':
+                cout << "Put message to selected topic: ";
+                cin >> cmd;
+                rep["message"] = cmd;
+                result = g_mqSelectedTopicResource->publishMQTopic(rep, query, &publishMessageCB,
+                         QualityOfService::LowQos);
+                break;
+
+            case '4':
+                cout << "Put topic uri to create: ";
+                cin >> cmd;
+                result = g_mqBrokerResource->createMQTopic(rep, cmd, query, &createTopicCB,
+                         QualityOfService::LowQos);
+                break;
+
+            case '5':
+                cout << "Put topic uri to create: ";
+                cin >> cmd;
+                cout << "Put topic type: ";
+                cin >> topicType;
+                query["rt"] = topicType;
+                result = g_mqBrokerResource->createMQTopic(rep, cmd, query, &createTopicCB,
+                         QualityOfService::LowQos);
+                break;
+
+            case 'q':
+                goto exit;
+                break;
+        }
+
+        if (result != OC_STACK_OK)
+        {
+            cout << "Error, return code: " << result << endl;
+        }
+    }
+
+exit:
+    return 0;
+}
\ No newline at end of file
diff --git a/cloud/samples/client/messagequeue/mq_subscriber.cpp b/cloud/samples/client/messagequeue/mq_subscriber.cpp
new file mode 100644 (file)
index 0000000..78d07ed
--- /dev/null
@@ -0,0 +1,249 @@
+//******************************************************************
+//
+// Copyright 2016 Samsung Electronics All Rights Reserved.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+///
+/// This sample provides the way to create cloud sample
+///
+#include <memory>
+#include <iostream>
+#include <stdexcept>
+#include <condition_variable>
+#include <map>
+#include <vector>
+#include <string>
+#include <unistd.h>
+#include <stdio.h>
+
+#include "ocstack.h"
+#include "ocpayload.h"
+
+#include <OCApi.h>
+#include <OCPlatform.h>
+
+using namespace OC;
+using namespace std;
+
+#define DEFAULT_MQ_BROKER_URI "/oic/ps"
+#define maxSequenceNumber 0xFFFFFF
+
+OC::OCResource::Ptr g_mqBrokerResource = nullptr;
+OC::OCResource::Ptr g_mqSelectedTopicResource = nullptr;
+
+vector<shared_ptr<OC::OCResource> > gTopicList;
+
+void printRepresentation(OCRepresentation rep)
+{
+    for (auto itr = rep.begin(); itr != rep.end(); ++itr)
+    {
+        cout << "\t" << itr->attrname() << ":\t" << itr->getValueToString() << endl;
+    }
+}
+
+////////////////////////////////////////Subscriber Sample
+void subscribeCB(const HeaderOptions &,
+                 const OCRepresentation &rep, const int eCode, const int sequenceNumber)
+{
+    try
+    {
+        if (eCode == OC_STACK_OK && sequenceNumber != maxSequenceNumber + 1)
+        {
+            if (sequenceNumber == OC_OBSERVE_REGISTER)
+            {
+                cout << "Observe registration action is successful" << endl;
+            }
+
+            cout << "OBSERVE RESULT:" << endl;
+            printRepresentation(rep);
+        }
+        else
+        {
+            if (eCode == OC_STACK_OK)
+            {
+                std::cout << "Observe registration failed or de-registration action failed/succeeded" << std::endl;
+            }
+            else
+            {
+                cout << "onObserve Response error: " << eCode << endl;
+                exit(-1);
+            }
+        }
+    }
+    catch (exception &e)
+    {
+        cout << "Exception: " << e.what() << " in onObserve" << endl;
+    }
+}
+
+void discoverTopicCB(const int ecode, const std::string &brokerUri,
+                     std::shared_ptr<OC::OCResource> topic)
+{
+    cout << "Topic discovered from " << brokerUri << " code: " << ecode << endl;
+    gTopicList.push_back(topic);
+    cout << "Topic [" << gTopicList.size() - 1 << "] " << topic->uri() << " discovered" << endl;
+}
+////////////////////////////////////////Subscriber Sample
+
+condition_variable  g_callbackLock;
+std::string             g_uid;
+std::string             g_accesstoken;
+
+void handleLoginoutCB(const HeaderOptions &,
+                      const OCRepresentation &rep, const int ecode)
+{
+    cout << "Auth response received code: " << ecode << endl;
+
+    if (rep.getPayload() != NULL)
+    {
+        printRepresentation(rep);
+    }
+
+    if (ecode == 4)
+    {
+        g_accesstoken = rep.getValueToString("accesstoken");
+
+        g_uid = rep.getValueToString("uid");
+    }
+
+    g_callbackLock.notify_all();
+}
+
+static FILE *client_open(const char * /*path*/, const char *mode)
+{
+    return fopen("./mq_subscriber.dat", mode);
+}
+
+int main(int argc, char *argv[])
+{
+    if (argc != 4 && argc != 5)
+    {
+        cout << "Put \"[host-ipaddress:port] [authprovider] [authcode]\" for sign-up and sign-in"
+             << endl;
+        cout << "Put \"[host-ipaddress:port] [uid] [accessToken] 1\" for sign-in" <<
+             endl;
+        return 0;
+    }
+
+    OCPersistentStorage ps{ client_open, fread, fwrite, fclose, unlink };
+
+    PlatformConfig cfg
+    {
+        ServiceType::InProc,
+        ModeType::Both,
+        "0.0.0.0", // By setting to "0.0.0.0", it binds to all available interfaces
+        0,         // Uses randomly available port
+        QualityOfService::LowQos,
+        &ps
+    };
+
+    OCPlatform::Configure(cfg);
+
+    OCStackResult result = OC_STACK_ERROR;
+
+    string host = "coap+tcp://";
+    host += argv[1];
+
+    OCAccountManager::Ptr accountMgr = OCPlatform::constructAccountManagerObject(host,
+                                       CT_ADAPTER_TCP);
+
+    mutex blocker;
+    unique_lock<std::mutex> lock(blocker);
+
+    if (argc == 5)
+    {
+        accountMgr->signIn(argv[2], argv[3], &handleLoginoutCB);
+        g_callbackLock.wait(lock);
+    }
+    else
+    {
+        accountMgr->signUp(argv[2], argv[3], &handleLoginoutCB);
+        g_callbackLock.wait(lock);
+        accountMgr->signIn(g_uid, g_accesstoken, &handleLoginoutCB);
+        g_callbackLock.wait(lock);
+    }
+
+    // MQ broker resource
+    g_mqBrokerResource = OCPlatform::constructResourceObject(host, DEFAULT_MQ_BROKER_URI,
+                         static_cast<OCConnectivityType>(CT_ADAPTER_TCP | CT_IP_USE_V4), false,
+    { string("oic.wk.ps") }, { string(DEFAULT_INTERFACE) });
+
+    cout << "===Message Queue subscriber sample===" << endl;
+    cout << "PUT 0 to discover all topics" << endl;
+    cout << "PUT 1 to discover type based topics" << endl;
+    cout << "PUT 2 to select topic for subscribing or unsubscribing" << endl;
+    cout << "PUT 3 to subscribe to selected topic" << endl;
+    cout << "PUT 4 to unsubscribe to selected topic" << endl;
+
+    string cmd;
+
+    while (true)
+    {
+        cin >> cmd;
+
+        QueryParamsMap query;
+        OCRepresentation rep;
+
+        switch (cmd[0])
+        {
+            case '0':
+                gTopicList.clear();
+                cout << "Discovering topics" << endl;
+                result = g_mqBrokerResource->discoveryMQTopics(query, &discoverTopicCB, QualityOfService::LowQos);
+                break;
+
+            case '1':
+                gTopicList.clear();
+                cout << "Put topic type to discover: ";
+                cin >> cmd;
+                query["rt"] = cmd;
+                result = g_mqBrokerResource->discoveryMQTopics(query, &discoverTopicCB, QualityOfService::LowQos);
+                break;
+
+            case '2':
+                cout << "Put discovered topic index to select: ";
+                cin >> cmd;
+                g_mqSelectedTopicResource = gTopicList[atoi(cmd.c_str())];
+                cout << g_mqSelectedTopicResource->uri() << " selected" << endl;
+                break;
+
+            case '3':
+                cout << "Subscribe to selected topic" << endl;
+                result = g_mqSelectedTopicResource->subscribeMQTopic(ObserveType::Observe, query, &subscribeCB,
+                         QualityOfService::LowQos);
+                break;
+
+            case '4':
+                cout << "Unsubscribe to selected topic" << endl;
+                result = g_mqSelectedTopicResource->unsubscribeMQTopic(QualityOfService::LowQos);
+                break;
+
+            case 'q':
+                goto exit;
+                break;
+        }
+
+        if (result != OC_STACK_OK)
+        {
+            cout << "Error, return code: " << result << endl;
+        }
+    }
+
+exit:
+    return 0;
+}
\ No newline at end of file