Includes C++ Presence Notification changes from Erich, Jesse, Sudarshan and Sashi.
authorSashi Penta <sashi.kumar.penta@intel.com>
Wed, 3 Sep 2014 03:17:01 +0000 (20:17 -0700)
committerSashi Penta <sashi.kumar.penta@intel.com>
Wed, 3 Sep 2014 03:18:30 +0000 (20:18 -0700)
Change-Id: I113cd2dc3051bace0d0111289184299e5fd21f87

14 files changed:
OCLib/InProcClientWrapper.cpp
OCLib/InProcServerWrapper.cpp
OCLib/OCPlatform.cpp
examples/makefile
examples/presenceclient.cpp [new file with mode: 0644]
examples/presenceserver.cpp [new file with mode: 0644]
include/IClientWrapper.h
include/IServerWrapper.h
include/InProcClientWrapper.h
include/InProcServerWrapper.h
include/OCPlatform.h
include/OutOfProcClientWrapper.h
include/OutOfProcServerWrapper.h
makefile

index 1bf1106..01a08fd 100644 (file)
@@ -590,4 +590,65 @@ namespace OC
 
         return result;
     }
-   }
+
+    struct SubscribePresenceContext
+    {
+        std::function<void(OCStackResult, const int&)> callback;
+    };
+
+    OCStackApplicationResult subscribePresenceCallback(void* ctx, OCDoHandle handle, OCClientResponse* clientResponse)
+    {
+        SubscribePresenceContext* context = static_cast<SubscribePresenceContext*>(ctx);
+        std::thread exec(context->callback, clientResponse->result, clientResponse->sequenceNumber);
+
+        exec.detach();
+        return OC_STACK_KEEP_TRANSACTION;
+    }
+
+    OCStackResult InProcClientWrapper::subscribePresence(OCDoHandle* handle, const std::string& host,
+                std::function<void(OCStackResult, const int&)> presenceHandler)
+    {
+        OCStackResult result;
+        OCCallbackData* cbdata = new OCCallbackData();
+        SubscribePresenceContext* ctx = new SubscribePresenceContext();
+        ctx->callback = presenceHandler;
+        cbdata->cb = &subscribePresenceCallback;
+        cbdata->context = static_cast<void*>(ctx);
+
+        auto cLock = m_csdkLock.lock();
+
+        std::ostringstream os;
+
+        os << host << "/oc/presence";
+
+        std::cout << "Subscribe Presence: " << os.str() << std::endl;
+
+        if(cLock)
+        {
+            result = OCDoResource(handle, OC_REST_PRESENCE, os.str().c_str(), nullptr, nullptr, OC_NON_CONFIRMABLE, cbdata);
+        }
+        else
+        {
+            return OC_STACK_ERROR;
+        }
+        return result;
+    }
+
+    OCStackResult InProcClientWrapper::unsubscribePresence(OCDoHandle handle)
+    {
+        OCStackResult result;
+        auto cLock = m_csdkLock.lock();
+        
+        if(cLock)
+        {
+            std::lock_guard<std::mutex> lock(*cLock);
+            result = OCCancel(handle);
+        }
+        else
+        {
+            result = OC_STACK_ERROR;
+        }
+
+        return result;
+    }
+}
index 6537524..fea13c3 100644 (file)
@@ -322,6 +322,39 @@ namespace OC
         return result;
     }
 
+    OCStackResult InProcServerWrapper::startPresence(const unsigned int seconds)
+    {
+        auto cLock = m_csdkLock.lock();
+        OCStackResult result = OC_STACK_ERROR;
+        if(cLock)
+        {
+            std::lock_guard<std::mutex> lock(*cLock);
+            result = OCStartPresence(seconds);
+        }
+        
+        if(result != OC_STACK_OK)
+        {
+            throw OCException("startPresence failed", result);
+        }
+        return result;
+    }
+
+    OCStackResult InProcServerWrapper::stopPresence()
+    {
+        auto cLock = m_csdkLock.lock();
+        OCStackResult result = OC_STACK_ERROR;
+        if(cLock)
+        {
+            std::lock_guard<std::mutex> lock(*cLock);
+            result = OCStopPresence();
+        }
+        
+        if(result != OC_STACK_OK)
+        {
+            throw OCException("stopPresence failed", result);
+        }
+        return result;
+    }
 
     InProcServerWrapper::~InProcServerWrapper()
     {
index e40c40d..ec272e4 100644 (file)
@@ -43,8 +43,9 @@ namespace OC
         init(m_cfg);
     }
 
-    OCPlatform::~OCPlatform()
+    OCPlatform::~OCPlatform(void)
     {
+        std::cout << "platform destructor called" << std::endl;
     }
 
     OCStackResult OCPlatform::notifyObservers(OCResourceHandle resourceHandle)
@@ -250,4 +251,53 @@ namespace OC
 
     }
 
+    OCStackResult OCPlatform::startPresence(const unsigned int announceDurationSeconds)            
+    { 
+        if(m_server)
+        {
+            return m_server->startPresence(announceDurationSeconds);
+        }
+        else
+        {
+            return OC_STACK_ERROR;
+        }
+    }
+
+    OCStackResult OCPlatform::stopPresence()
+    {
+        if(m_server)
+        {
+            return m_server->stopPresence();
+        }
+        else
+        {
+            return OC_STACK_ERROR;
+        }
+    }
+
+    OCStackResult OCPlatform::subscribePresence(OCPresenceHandle& presenceHandle, const std::string& host, 
+                    std::function<void(OCStackResult, const int&)> presenceHandler)
+    {
+        if(m_client)
+        {
+            return m_client->subscribePresence(&presenceHandle, host, presenceHandler);
+        }
+        else
+        {
+            return OC_STACK_ERROR;
+        }
+    }
+
+    OCStackResult OCPlatform::unsubscribePresence(OCPresenceHandle presenceHandle)
+    {
+        if(m_client)
+        {
+            return m_client->unsubscribePresence(presenceHandle);
+        }
+        else
+        {
+            return OC_STACK_ERROR;
+        }
+    }
+
 } //namespace OC
index da740ff..37f7469 100644 (file)
@@ -5,7 +5,7 @@ CXX           := g++
 #CXX     := clang
 OUT_DIR          := $(PWD)/$(BUILD)
 
-CXX_FLAGS.debug     := -O0 -g3 -std=c++0x -Wall -pthread
+CXX_FLAGS.debug     := -O0 -g3 -std=c++0x -Wall -pthread 
 
 CXX_FLAGS.release   := -O3 -std=c++0x -Wall -pthread 
 
@@ -17,7 +17,7 @@ CXX_INC         += -I../csdk/logger/include
 CXX_INC          += -I../csdk/libcoap
 
 # Force metatargets to build:
-.PHONY: prep_dirs simpleserver simpleclient simpleclientserver roomserver roomclient ocicuc
+.PHONY: prep_dirs simpleserver simpleclient simpleclientserver roomserver roomclient ocicuc presenceserver presenceclient
 
 all: .PHONY
 
@@ -30,6 +30,12 @@ simpleserver: simpleserver.cpp
 simpleclient: simpleclient.cpp
        $(CXX) $(CXX_FLAGS.$(BUILD)) -o $(OUT_DIR)/$@ simpleclient.cpp $(CXX_INC) ../$(BUILD)/obj/OCLib.a ../csdk/$(BUILD)/liboctbstack.a
 
+presenceserver: presenceserver.cpp
+       $(CXX) $(CXX_FLAGS.$(BUILD)) -o $(OUT_DIR)/$@ presenceserver.cpp $(CXX_INC) ../$(BUILD)/obj/OCLib.a ../csdk/$(BUILD)/liboctbstack.a
+
+presenceclient: presenceclient.cpp
+       $(CXX) $(CXX_FLAGS.$(BUILD)) -o $(OUT_DIR)/$@ presenceclient.cpp $(CXX_INC) ../$(BUILD)/obj/OCLib.a ../csdk/$(BUILD)/liboctbstack.a
+
 simpleclientserver: simpleclientserver.cpp
        $(CXX) $(CXX_FLAGS.$(BUILD)) -o $(OUT_DIR)/$@ simpleclientserver.cpp $(CXX_INC) ../$(BUILD)/obj/OCLib.a ../csdk/$(BUILD)/liboctbstack.a
 
diff --git a/examples/presenceclient.cpp b/examples/presenceclient.cpp
new file mode 100644 (file)
index 0000000..37bff7d
--- /dev/null
@@ -0,0 +1,182 @@
+//******************************************************************
+//
+// Copyright 2014 Intel Mobile Communications GmbH 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.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+// PresenceClient.cpp : A client example for presence notification
+//
+#include <string>
+#include <cstdlib>
+#include <pthread.h>
+#include "OCPlatform.h"
+#include "OCApi.h"
+
+using namespace OC;
+
+const int SUCCESS_RESPONSE = 0;
+std::shared_ptr<OCResource> curResource;
+static ObserveType OBSERVE_TYPE_TO_USE = ObserveType::Observe;
+
+OCPlatform* platformPtr;
+
+// Callback to presence
+void presenceHandler(OCStackResult result, const int& nonce)
+{
+    switch(result)
+    {
+        case OC_STACK_OK:
+            std::cout << "Nonce# " << nonce << std::endl;
+            break;
+        case OC_STACK_PRESENCE_NO_UPDATE:
+            std::cout << "No presence updated\n";
+            break;
+        case OC_STACK_PRESENCE_STOPPED:
+            std::cout << "Presence Stopped\n";
+            break;
+        case OC_STACK_PRESENCE_DO_NOT_HANDLE:
+            std::cout << "Presence do not handle\n";
+            break;
+        default:
+            std::cout << "Error\n";
+            break;
+    }
+}
+
+// Callback to found resources
+void foundResource(std::shared_ptr<OCResource> resource)
+{
+
+    if(curResource)
+    {
+        std::cout << "Found another resource, ignoring"<<std::endl;
+    }
+
+    std::string resourceURI;
+    std::string hostAddress;
+    try
+    {
+        // Do some operations with resource object.
+        if(resource)
+        {
+            std::cout<<"DISCOVERED Resource:"<<std::endl;
+            // Get the resource URI
+            resourceURI = resource->uri();
+            std::cout << "\tURI of the resource: " << resourceURI << std::endl;
+
+            // Get the resource host address
+            hostAddress = resource->host();
+            std::cout << "\tHost address of the resource: " << hostAddress << std::endl;
+
+            // Get the resource types 
+            std::cout << "\tList of resource types: " << std::endl;
+            for(auto &resourceTypes : resource->getResourceTypes())
+            {
+                std::cout << "\t\t" << resourceTypes << std::endl;
+            }
+            
+            // Get the resource interfaces
+            std::cout << "\tList of resource interfaces: " << std::endl;
+            for(auto &resourceInterfaces : resource->getResourceInterfaces())
+            {
+                std::cout << "\t\t" << resourceInterfaces << std::endl;
+            } 
+
+            if(resourceURI == "/a/light")
+            {
+                curResource = resource;
+                OCPlatform::OCPresenceHandle presenceHandle;
+                platformPtr->subscribePresence(presenceHandle, hostAddress, &presenceHandler);
+            }
+        }
+        else
+        {
+            // Resource is invalid
+            std::cout << "Resource is invalid" << std::endl;
+        }
+
+    }
+    catch(std::exception& e)
+    {
+        //log(e.what());
+    }
+}
+
+void PrintUsage()
+{
+    std::cout << std::endl;
+    std::cout << "Usage : simpleclient <ObserveType>" << std::endl;
+    std::cout << "   ObserveType : 1 - Observe" << std::endl;
+    std::cout << "   ObserveType : 2 - ObserveAll" << std::endl;
+}
+
+
+int main(int argc, char* argv[]) {
+    if (argc == 1)
+    {
+        OBSERVE_TYPE_TO_USE = ObserveType::Observe;
+    }
+    else if (argc == 2)
+    {
+        int value = atoi(argv[1]);
+        if (value == 1)
+            OBSERVE_TYPE_TO_USE = ObserveType::Observe;
+        else if (value == 2)
+            OBSERVE_TYPE_TO_USE = ObserveType::ObserveAll;
+        else
+            OBSERVE_TYPE_TO_USE = ObserveType::Observe;
+    }
+    else
+    {
+        PrintUsage();
+        return -1;
+    }
+
+    // Create PlatformConfig object
+    PlatformConfig cfg {
+        OC::ServiceType::InProc,
+        OC::ModeType::Client,
+        "192.168.1.10",
+        5683,
+        OC::QualityOfService::NonConfirmable
+    };
+
+    // Create a OCPlatform instance.
+    // Note: Platform creation is synchronous call.
+
+    try
+    {
+        OCPlatform platform(cfg);
+        // PlatformPtr is used in another function
+        platformPtr = &platform;
+        std::cout << "Created Platform..."<<std::endl;
+        // Find all resources
+        platform.findResource("", "coap://224.0.1.187/oc/core", &foundResource);
+        std::cout<< "Finding Resource... " <<std::endl;
+        while(true)
+        {
+            // some operations
+        }
+
+    }catch(OCException& e)
+    {
+        //log(e.what());
+    }
+
+    return 0;
+}
+
diff --git a/examples/presenceserver.cpp b/examples/presenceserver.cpp
new file mode 100644 (file)
index 0000000..306b960
--- /dev/null
@@ -0,0 +1,342 @@
+//******************************************************************
+//
+// Copyright 2014 Intel Mobile Communications GmbH 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 steps to define an interface for a resource
+/// (properties and methods) and host this resource on the server.
+///
+
+#include <functional>
+
+#include <pthread.h>
+
+#include "OCPlatform.h"
+#include "OCApi.h"
+
+using namespace OC;
+using namespace std;
+
+// Forward declaring the entityHandler
+void entityHandler(std::shared_ptr<OCResourceRequest> request, std::shared_ptr<OCResourceResponse> response);
+
+/// This class represents a single resource named 'lightResource'. This resource has
+/// two simple properties named 'state' and 'power'
+
+class LightResource
+{
+public:
+    /// Access this property from a TB client
+    bool m_state;
+    int m_power;
+    std::string m_lightUri;
+    std::string m_lightUri2;
+    OCResourceHandle m_resourceHandle;
+    OCResourceHandle m_resourceHandle2;
+
+public:
+    /// Constructor
+    LightResource(): m_state(false), m_power(0), m_lightUri("/a/light"), m_lightUri2("/a/light2") {}
+
+    /* Note that this does not need to be a member function: for classes you do not have
+    access to, you can accomplish this with a free function: */
+
+    /// This function internally calls registerResource API.
+    void createResource(OC::OCPlatform& platform)
+    {
+        std::string resourceURI = m_lightUri; // URI of the resource
+        std::string resourceTypeName = "core.light"; // resource type name. In this case, it is light
+        std::string resourceInterface = DEFAULT_INTERFACE; // resource interface.
+
+        // OCResourceProperty is defined ocstack.h
+        uint8_t resourceProperty = OC_DISCOVERABLE | OC_OBSERVABLE;
+
+        // This will internally create and register the resource.
+        OCStackResult result = platform.registerResource(
+                                    m_resourceHandle, resourceURI, resourceTypeName,
+                                    resourceInterface, &entityHandler, resourceProperty);
+
+        if (OC_STACK_OK != result)
+        {
+            cout << "Resource creation was unsuccessful\n";
+        }
+    }
+
+    /// This function internally calls registerResource API.
+    void createResource2(OC::OCPlatform& platform)
+    {
+        std::string resourceURI = m_lightUri2; // URI of the resource
+        std::string resourceTypeName = "core.light"; // resource type name. In this case, it is light
+        std::string resourceInterface = DEFAULT_INTERFACE; // resource interface.
+
+        // OCResourceProperty is defined ocstack.h
+        uint8_t resourceProperty = OC_DISCOVERABLE | OC_OBSERVABLE;
+
+        // This will internally create and register the resource.
+        OCStackResult result = platform.registerResource(
+                                    m_resourceHandle2, resourceURI, resourceTypeName,
+                                    resourceInterface, &entityHandler, resourceProperty);
+
+        if (OC_STACK_OK != result)
+        {
+            cout << "Resource creation was unsuccessful\n";
+        }
+    }
+
+    OCResourceHandle getHandle()
+    {
+        return m_resourceHandle;
+    }
+
+    void setRepresentation(OCRepresentation& light)
+    {
+        AttributeMap attributeMap = light.getAttributeMap();
+
+        if(attributeMap.find("state") != attributeMap.end() && attributeMap.find("power") != attributeMap.end())
+        {
+            cout << "\t\t\t" << "Received representation: " << endl;
+            cout << "\t\t\t\t" << "power: " << attributeMap["power"][0] << endl;
+            cout << "\t\t\t\t" << "state: " << attributeMap["state"][0] << endl;
+
+            m_state = attributeMap["state"][0].compare("true") == 0;
+            m_power= std::stoi(attributeMap["power"][0]);
+        }
+    }
+
+    OCRepresentation getRepresentation()
+    {
+        OCRepresentation light;
+
+        light.setUri(m_lightUri);
+
+        std::vector<std::string> interfaces;
+        //interfaces.push_back(m_lightInterface);
+
+        light.setResourceInterfaces(interfaces);
+
+        std::vector<std::string> types;
+        //types.push_back(m_lightType);
+
+        light.setResourceTypes(types);
+
+        AttributeMap attributeMap;
+        AttributeValues stateVal;
+        if(m_state)
+        {
+            stateVal.push_back("true");
+        }
+        else
+        {
+            stateVal.push_back("false");
+        }
+
+        AttributeValues powerVal;
+        powerVal.push_back(to_string(m_power));
+
+        attributeMap["state"] = stateVal;
+        attributeMap["power"] = powerVal;
+
+        light.setAttributeMap(attributeMap);
+
+        return light;
+    }
+
+    void addType(const OC::OCPlatform& platform, const std::string& type) const
+    {
+        OCStackResult result = platform.bindTypeToResource(m_resourceHandle, type);
+        if (OC_STACK_OK != result)
+        {
+            cout << "Binding TypeName to Resource was unsuccessful\n";
+        }
+    }
+
+    void addInterface(const OC::OCPlatform& platform, const std::string& interface) const
+    {
+        OCStackResult result = platform.bindInterfaceToResource(m_resourceHandle, interface);
+        if (OC_STACK_OK != result)
+        {
+            cout << "Binding TypeName to Resource was unsuccessful\n";
+        }
+    }
+};
+
+// Create the instance of the resource class (in this case instance of class 'LightResource').
+LightResource myLightResource;
+
+// This is just a sample implementation of entity handler.
+// Entity handler can be implemented in several ways by the manufacturer
+void entityHandler(std::shared_ptr<OCResourceRequest> request, std::shared_ptr<OCResourceResponse> response)
+{
+    cout << "\tIn Server CPP entity handler:\n";
+
+    if(request)
+    {
+        // Get the request type and request flag
+        std::string requestType = request->getRequestType();
+        RequestHandlerFlag requestFlag = request->getRequestHandlerFlag();
+
+        if(requestFlag == RequestHandlerFlag::InitFlag)
+        {
+            cout << "\t\trequestFlag : Init\n";
+
+            // entity handler to perform resource initialization operations
+        }
+        else if(requestFlag == RequestHandlerFlag::RequestFlag)
+        {
+            cout << "\t\trequestFlag : Request\n";
+
+            // If the request type is GET
+            if(requestType == "GET")
+            {
+                cout << "\t\t\trequestType : GET\n";
+
+                // Check for query params (if any)
+                QueryParamsMap queryParamsMap = request->getQueryParameters();
+
+                cout << "\t\t\tquery params: \n";
+                for(QueryParamsMap::iterator it = queryParamsMap.begin(); it != queryParamsMap.end(); it++)
+                {
+                    cout << "\t\t\t\t" << it->first << ":" << it->second << endl;
+                }
+
+                // Process query params and do required operations ..
+
+                // Get the representation of this resource at this point and send it as response
+                // AttributeMap attributeMap;
+                OCRepresentation rep;
+                rep = myLightResource.getRepresentation();
+
+                if(response)
+                {
+                    // TODO Error Code
+                    response->setErrorCode(200);
+
+                    auto findRes = queryParamsMap.find("if");
+
+                    if(findRes != queryParamsMap.end())
+                    {
+                        response->setResourceRepresentation(rep, findRes->second);
+                    }
+                    else
+                    {
+                        response->setResourceRepresentation(rep, DEFAULT_INTERFACE);
+                    }
+                }
+            }
+            else if(requestType == "PUT")
+            {
+                cout << "\t\t\trequestType : PUT\n";
+
+                // Check for query params (if any)
+                QueryParamsMap queryParamsMap = request->getQueryParameters();
+
+                cout << "\t\t\tquery params: \n";
+                for(auto it = queryParamsMap.begin(); it != queryParamsMap.end(); it++)
+                {
+                    cout << "\t\t\t\t" << it->first << ":" << it->second << endl;
+                }
+
+                // Get the representation from the request
+                OCRepresentation rep = request->getResourceRepresentation();
+
+                myLightResource.setRepresentation(rep);
+
+                // Do related operations related to PUT request
+                rep = myLightResource.getRepresentation();
+
+                if(response)
+                {
+                    // TODO Error Code
+                    response->setErrorCode(200);
+
+                    auto findRes = queryParamsMap.find("if");
+
+                    if(findRes != queryParamsMap.end())
+                    {
+                        response->setResourceRepresentation(rep, findRes->second);
+                    }
+                    else
+                    {
+                        response->setResourceRepresentation(rep, DEFAULT_INTERFACE);
+                    }
+                }
+
+            }
+            else if(requestType == "POST")
+            {
+                // POST request operations
+            }
+            else if(requestType == "DELETE")
+            {
+                // DELETE request operations
+            }
+        }
+        else if(requestFlag == RequestHandlerFlag::ObserverFlag)
+        {
+            // OBSERVE flag operations
+        }
+    }
+    else
+    {
+        std::cout << "Request invalid" << std::endl;
+    }
+}
+
+int main()
+{
+    // Create PlatformConfig object
+    PlatformConfig cfg {
+        OC::ServiceType::InProc,
+        OC::ModeType::Server,
+        "134.134.161.33",
+        56832,
+        OC::QualityOfService::NonConfirmable
+    };
+
+    // Create a OCPlatform instance.
+    // Note: Platform creation is synchronous call.
+    try
+    {
+        OCPlatform platform(cfg);
+
+        // Time to Live is 100
+        platform.startPresence(100);
+
+        // Invoke createResource function of class light.
+        myLightResource.createResource(platform);
+
+        printf("Enter a key to create the second resource\n");
+        getchar();
+
+        myLightResource.createResource2(platform);
+
+        // Perform app tasks
+        while(true)
+        {
+            // some tasks
+        }
+    }
+    catch(OCException e)
+    {
+        //log(e.what());
+    }
+
+    // No explicit call to stop the platform.
+    // When OCPlatform destructor is invoked, internally we do platform cleanup
+}
index 3cbf998..471d26e 100644 (file)
@@ -48,6 +48,11 @@ namespace OC
         
         virtual OCStackResult CancelObserveResource(OCDoHandle handle, const std::string& host, const std::string& uri)=0;
         
+        virtual OCStackResult subscribePresence(OCDoHandle* handle, const std::string& host, 
+            std::function<void(OCStackResult, const int&)> presenceHandler)=0;
+
+        virtual OCStackResult unsubscribePresence(OCDoHandle handle) =0;
+
         virtual ~IClientWrapper(){}
        
 
index e615802..b102329 100644 (file)
@@ -55,6 +55,10 @@ namespace OC
         virtual OCStackResult bindInterfaceToResource(
                     const OCResourceHandle& resourceHandle,
                     const std::string& resourceInterfaceName) = 0;
+
+        virtual OCStackResult startPresence(const unsigned int seconds) = 0;
+
+        virtual OCStackResult stopPresence() = 0;
     };
 }
 
index 9b82e44..fac0c0a 100644 (file)
@@ -58,6 +58,10 @@ namespace OC
         
         virtual OCStackResult CancelObserveResource(OCDoHandle handle, const std::string& host, const std::string& uri);
         
+        virtual OCStackResult subscribePresence(OCDoHandle* handle, const std::string& host,
+            std::function<void(OCStackResult, const int&)> presenceHandler);
+
+        virtual OCStackResult unsubscribePresence(OCDoHandle handle);
         // Note: this should never be called by anyone but the handler for the listen command.  It is public becuase that needs to be a non-instance callback
         virtual std::shared_ptr<OCResource> parseOCResource(IClientWrapper::Ptr clientWrapper, const std::string& host, const boost::property_tree::ptree resourceNode);
     private:
index a34e62f..bcd85eb 100644 (file)
@@ -52,6 +52,10 @@ namespace OC
         virtual OCStackResult bindInterfaceToResource(
                     const OCResourceHandle& resourceHandle,
                     const std::string& resourceInterface);
+
+        virtual OCStackResult startPresence(const unsigned int seconds);
+
+        virtual OCStackResult stopPresence();
     private:
         void processFunc();
         std::thread m_processThread;
index f57910c..e39fae0 100644 (file)
@@ -47,6 +47,9 @@ namespace OC
     class OCPlatform
     {
     public:
+        // typedef for handle to cancel presence info with
+        typedef OCDoHandle OCPresenceHandle;
+
         /**
         * Constructor for OCPlatform. Constructs a new OCPlatform from a given PlatformConfig with
         * appropriate fields
@@ -212,7 +215,7 @@ namespace OC
         * @param resourceHandle - handle to the resource
         * @param resourceTypeName - new typename to bind to the resource
 
-        * @return OCStackResult - return value of the API. Returns OCSTACk_OK if success <br>
+        * @return OCStackResult - return value of the API. Returns OCSTACK_OK if success <br>
         */
         OCStackResult bindTypeToResource(const OCResourceHandle& resourceHandle,
                         const std::string& resourceTypeName) const;
@@ -222,11 +225,52 @@ namespace OC
         * @param resourceHandle - handle to the resource
         * @param resourceTypeName - new interface  to bind to the resource
 
-        * @return OCStackResult - return value of the API. Returns OCSTACk_OK if success <br>
+        * @return OCStackResult - return value of the API. Returns OCSTACK_OK if success <br>
         */
         OCStackResult bindInterfaceToResource(const OCResourceHandle& resourceHandle,
                         const std::string& resourceInterfaceName) const;
 
+        public:
+        /** 
+        * Start or stop Presence announcements. 
+        * 
+        * @param announceDuration - Duration to keep presence duration active.
+        * @return OCStackResult - Returns OCSTACK_OK if success <br>
+        *
+        * These apply only if a server instance is active.
+        */
+        OCStackResult startPresence(const unsigned int announceDurationSeconds);
+
+        OCStackResult stopPresence();
+
+        /**
+        * subscribes to a server's presence change events.  By making this subscription,
+        * every time a server adds/removes/alters a resource, starts or is intentionally
+        * stopped (potentially more to be added later).
+        *
+        * @param presenceHandle - a handle object that can be used to identify this subscription
+        *               request.  It can be used to unsubscribe from these events in the future. 
+        *               It will be set upon successful return of this method.
+        * @param host - The IP address/addressable name of the server to subscribe to.
+        * @param presenceHandler - callback function that will receive notifications/subscription events
+        *
+        * @return OCStackResult - return value of the API.  Returns OCSTACK_OK if success <br>
+        */
+        OCStackResult subscribePresence(OCPresenceHandle& presenceHandle, const std::string& host, 
+                        std::function<void(OCStackResult, const int&)> presenceHandler);
+
+        /**
+        * unsubscribes from a previously subscribed server's presence events. Note that
+        * you may for a short time still receive events from the server since it may take time
+        * for the unsubscribe to take effect.
+        *
+        * @param presenceHandle - the handle object provided by the subscribePresence call that identifies
+        *               this subscription.
+        *
+        * @return OCStackResult - return value of the API.  Returns OCSTACK_OK if success <br>
+        */
+        OCStackResult unsubscribePresence(OCPresenceHandle presenceHandle);
+
         /**
         * Creates a resource proxy object so that get/put/observe functionality
         * can be used without discovering the object in advance.  Note that the
index 02ee7f9..7333bcf 100644 (file)
@@ -50,6 +50,11 @@ namespace OC
 
         virtual std::shared_ptr<OCResource> parseOCResource(IClientWrapper::Ptr clientWrapper, const std::string& host, 
             const boost::property_tree::ptree resourceNode) {return nullptr;}
+
+        virtual OCStackResult subscribePresence(OCDoHandle* handle, const std::string& host,
+            std::function<void(OCStackResult, const int&)> presenceHandler){return OC_STACK_NOTIMPL;}
+
+        virtual OCStackResult unsubscribePresence(OCDoHandle handle){return OC_STACK_NOTIMPL;}
     };
 }
 
index c915042..3c2108f 100644 (file)
@@ -40,20 +40,30 @@ namespace OC
 
         {
             // Not implemented
-            return OC_STACK_ERROR;
+            return OC_STACK_NOTIMPL;
         }
         virtual OCStackResult bindTypeToResource(
                      const OCResourceHandle& resourceHandle,
                      const std::string& resourceTypeName)
         {   //Not implemented yet
-            return OC_STACK_ERROR;
+            return OC_STACK_NOTIMPL;
         }
 
         virtual OCStackResult bindInterfaceToResource(
                      const OCResourceHandle& resourceHandle,
                      const std::string& resourceInterfaceName)
         {   //Not implemented yet
-            return OC_STACK_ERROR;
+            return OC_STACK_NOTIMPL;
+        }
+
+        virtual OCStackResult startPresence(const unsigned int seconds)
+        {   //Not implemented yet
+            return OC_STACK_NOTIMPL;
+        }
+
+        virtual OCStackResult stopPresence()
+        {   //Not implemented yet
+            return OC_STACK_NOTIMPL;
         }
     };
 }
index 1f7a3e5..1add828 100644 (file)
--- a/makefile
+++ b/makefile
@@ -1,4 +1,4 @@
-# override with `make BUILD=release`
+# override with `make BUILD=debug`
 # default to release build
 BUILD    := release
 CXX          := g++
@@ -6,9 +6,8 @@ CXX           := g++
 OUT_DIR          := $(PWD)/$(BUILD)
 OBJ_DIR          := $(OUT_DIR)/obj
 
-CXX_FLAGS.debug     := -g3 -std=c++0x -Wall -pthread -O0
-
-CXX_FLAGS.release   := -std=c++0x -Wall -pthread -O3
+CXX_FLAGS.debug     := -g3 -std=c++0x -Wall -pthread -O0 
+CXX_FLAGS.release   := -std=c++0x -Wall -pthread -O3 
 
 CXX_INC          := -I./include/
 CXX_INC          += -I./csdk/stack/include