[SECARSP-269] Policies state handler for device agent implemented. Tizen ID used...
authorDmytro Lomtiev <d.lomtev@samsung.com>
Wed, 28 Mar 2018 08:02:30 +0000 (11:02 +0300)
committerDmytro Lomtiev <d.lomtev@samsung.com>
Wed, 28 Mar 2018 08:12:28 +0000 (11:12 +0300)
18 files changed:
device-agent/communication/inc/connection.h
device-agent/communication/inc/eventlistener.h
device-agent/communication/inc/irestservice.h
device-agent/communication/inc/restservice.h
device-agent/communication/inc/settings.h
device-agent/communication/inc/sysinfo.h
device-agent/communication/src/connection.cpp
device-agent/communication/src/reportcomposer.cpp
device-agent/communication/src/restservice.cpp
device-agent/communication/src/settings.cpp
device-agent/communication/src/sysinfo.cpp
device-agent/daemon/main_thread.cpp
device-agent/daemon/policyhandler.h
device-agent/daemon/policystatehandler.cpp [new file with mode: 0644]
device-agent/daemon/policystatehandler.h [new file with mode: 0644]
device-agent/utest/mock/restservicemock.h
device-agent/utest/test_connection.cpp
device-agent/utest/test_settings.cpp

index 662a380..cc2a903 100644 (file)
@@ -74,6 +74,12 @@ public:
     void confirm(const std::string& uri, const std::string& response) const;
 
     /**
+     * @brief sendData sends data to the server
+     * @param data data to send
+     */
+    void sendData(const Json::Value& data) const;
+
+    /**
      * @brief loop event processing loop
      * @note the method blocks execution until Connection::stop() method is called
      */
index 685a5c5..d8a1ada 100644 (file)
@@ -47,8 +47,9 @@ public:
      * @param event event to process
      */
     virtual void accept(Event& event) = 0;
-private:
+protected:
     Connection& connection;
+private:
     int id;
 };
 
index ddd5b54..29a3b23 100644 (file)
@@ -72,18 +72,18 @@ public:
     virtual void doPost(const SessionInfo& info, const std::string& uri, const std::string& data) = 0;
 
     /**
-     * @brief sendReport sends report to the DSM server
+     * @brief sendData sends data to the DSM server
      * @param info session information
-     * @param report JSON document the contains the reports
+     * @param data data to send
      */
-    virtual void sendReport(const SessionInfo& info, const std::string& report) = 0;
+    virtual void sendData(const SessionInfo& info, const std::string& data) = 0;
 
     /**
-     * @brief sendReport sends report to the DSM server
+     * @brief sendData sends data to the DSM server
      * @param info session information
-     * @param report JSON object the contains the reports
+     * @param data JSON object to send
      */
-    virtual void sendReport(const SessionInfo& info, const Json::Value& report) = 0;
+    virtual void sendData(const SessionInfo& info, const Json::Value& data) = 0;
 };
 
 }
index b9a22cb..1824a8d 100644 (file)
@@ -42,9 +42,9 @@ public:
 
     void doPost(const SessionInfo& info, const std::string& uri, const std::string& data) override;
 
-    void sendReport(const SessionInfo& info, const std::string& report) override;
+    void sendData(const SessionInfo& info, const std::string& data) override;
 
-    void sendReport(const SessionInfo& info, const Json::Value& report) override;
+    void sendData(const SessionInfo& info, const Json::Value& data) override;
 private:
     std::string host;
 };
index 3b3312d..4459252 100644 (file)
@@ -58,15 +58,6 @@ public:
     }
 
     /**
-     * @brief getSerial returns the device serial number
-     * @return serial number as string
-     */
-    const std::string& getSerial() const
-    {
-        return serial;
-    }
-
-    /**
      * @brief setServerAddress sets the address of the DSM server
      * @param address DSM server URL
      */
@@ -167,7 +158,6 @@ private:
 
     std::string serverAddress;
     std::string deviceId;
-    std::string serial;
     std::chrono::milliseconds keepAliveTimeout;
     std::string saveFileName;
     bool loaded;
index 8f2a963..37b230e 100644 (file)
@@ -52,6 +52,12 @@ public:
      * @return software version as string on success and "undefined" otherwise
      */
     static std::string swVersion();
+
+    /**
+     * @brief tizenId returns tizen ID of the device
+     * @return tizen id as string on success and "undefined" otherwise
+     */
+    static std::string tizenId();
 };
 
 } // namespace NetworkManager
index 819f710..40c7334 100644 (file)
@@ -103,7 +103,7 @@ void Connection::loop()
 
                     lock.unlock();
                     try {
-                        rest->sendReport(sinfo, composer.get());
+                        rest->sendData(sinfo, composer.get());
                     } catch (std::exception& e) {
                         LOG_E(TAG, "Fail to send report: %s", e.what());
                     }
@@ -111,48 +111,52 @@ void Connection::loop()
             } while(0);
 
             if (next <= clock.now()) {
-                std::string updates = rest->getUpdates(sinfo);
-                LOG_D(TAG, "Updates: %s", updates.c_str());
+                try {
+                    std::string updates = rest->getUpdates(sinfo);
+                    LOG_D(TAG, "Updates: %s", updates.c_str());
 
-                if (updates.empty()) {
-                    break;
-                }
-
-                Json::Reader reader;
-                Json::Value root;
-
-                if (!reader.parse(updates, root)) {
-                    LOG_E(TAG, "Malformed JSON");
-                } else {
-                    if (!root.isArray()) {
-                        LOG_D(TAG, "Update information must be an array.");
+                    if (updates.empty()) {
                         break;
                     }
 
-                    for (const auto& item: root) {
-                        Event event(item, *this);
+                    Json::Reader reader;
+                    Json::Value root;
 
-                        if (!event.isValid()) {
-                            LOG_E(TAG, "Update event is invalid");
-                            continue;
+                    if (!reader.parse(updates, root)) {
+                        LOG_E(TAG, "Malformed JSON");
+                    } else {
+                        if (!root.isArray()) {
+                            LOG_D(TAG, "Update information must be an array.");
+                            break;
                         }
 
-                        LOG_D(TAG, "Update type: %s", event.getType().c_str());
+                        for (const auto& item: root) {
+                            Event event(item, *this);
+
+                            if (!event.isValid()) {
+                                LOG_E(TAG, "Update event is invalid");
+                                continue;
+                            }
 
-                        try {
-                            auto found_listeners = listeners.find(event.getType());
+                            LOG_D(TAG, "Update type: %s", event.getType().c_str());
 
-                            if (found_listeners != listeners.end()) {
-                                LOG_D(TAG, "Found listeners");
+                            try {
+                                auto found_listeners = listeners.find(event.getType());
 
-                                for (auto it = found_listeners->second.begin(); it != found_listeners->second.end(); ++it) {
-                                    (*it)->accept(event);
+                                if (found_listeners != listeners.end()) {
+                                    LOG_D(TAG, "Found listeners");
+
+                                    for (auto it = found_listeners->second.begin(); it != found_listeners->second.end(); ++it) {
+                                        (*it)->accept(event);
+                                    }
                                 }
+                            } catch (std::exception& e) {
+                                LOG_E(TAG, "Failed to get update content \"%s\". Error: %s", event.getDescription().c_str(), e.what());
                             }
-                        } catch (std::exception& e) {
-                            LOG_E(TAG, "Failed to get update content \"%s\". Error: %s", event.getDescription().c_str(), e.what());
                         }
                     }
+                } catch (std::exception& e) {
+                    LOG_E(TAG, "Connection Work loop exception: %s", e.what());
                 }
             }
             break;
@@ -182,6 +186,11 @@ void Connection::confirm(const std::string& uri, const std::string& response) co
     }
 }
 
+void Connection::sendData(const Json::Value& data) const
+{
+    rest->sendData(sinfo, data);
+}
+
 bool Connection::reg()
 {
     try {
index 1379e04..881f5b5 100644 (file)
 namespace NetworkManager
 {
 
-ReportComposer::ReportComposer(): root(Json::arrayValue)
+ReportComposer::ReportComposer(): root()
 {
+    root["type"] = std::string{"report"};
+    root["data"] = Json::Value(Json::arrayValue);
 }
 
 void ReportComposer::addEvent(const ReportEvent& event)
@@ -26,7 +28,7 @@ void ReportComposer::addEvent(const ReportEvent& event)
     item["module"] = event.first;
     item["log"] = event.second;
 
-    root.append(item);
+    root["data"].append(item);
 }
 
 std::string ReportComposer::str()
index c1f2f5c..a569d85 100644 (file)
@@ -73,7 +73,7 @@ std::string RestService::registerDevice(const SessionInfo& info)
 {
     RestRequest request(host);
     Json::Value root;
-    root["sn"] = Settings::instance().getSerial();
+    root["sn"] = SysInfo::tizenId();
     root["model"] = SysInfo::model();
     root["type"] = SysInfo::type();
     root["sw"] = SysInfo::swVersion();
@@ -111,24 +111,20 @@ void RestService::doPost(const SessionInfo& info, const std::string& uri, const
     restResultGuard(request.post(RestRequest::QueryParameters{}, uri, data));
 }
 
-void RestService::sendReport(const SessionInfo& info, const std::string& report)
+void RestService::sendData(const SessionInfo& info, const std::string& data)
 {
-    sendReport(info, Json::Value(report));
+    LOG_D(TAG, "Request body: %s", data.c_str());
+    RestRequest request(host);
+    request.addHeader("Content-Type", "application/json");
+    restResultGuard(request.post(RestRequest::QueryParameters{{"duid", info.duid}}, SEND_DATA_REST_API, data));
+    LOG_D(TAG, "Response: %s", request.body().c_str());
 }
 
-void RestService::sendReport(const SessionInfo& info, const Json::Value& report)
+void RestService::sendData(const SessionInfo& info, const Json::Value& data)
 {
-    RestRequest request(host);
-    Json::Value root;
-    root["type"] = "report";
-    root["data"] = report;
-
     Json::FastWriter writer;
-    std::string payload = writer.write(root);
-    LOG_D(TAG, "Request body: %s", payload.c_str());
-    request.addHeader("Content-Type", "application/json");
-    restResultGuard(request.post(RestRequest::QueryParameters{{"duid", info.duid}}, SEND_DATA_REST_API, payload));
-    LOG_D(TAG, "Response: %s", request.body().c_str());
+    std::string payload = writer.write(data);
+    sendData(info, payload);
 }
 
 }
index 9944863..1d519ef 100644 (file)
@@ -34,25 +34,8 @@ const std::string DEFAULT_STRING_PROPERTY{"unknown"};
 const std::string PROPKEY_SERVER_ADDR{"Server.URL"};
 const std::string PROPKEY_KEEPALIVE{"Server.keepalive"};
 const std::string PROPKEY_DUID{"Device.id"};
-const std::string PROPKEY_SERIAL{"Device.serial"};
 const std::string PROPKEY_LOCK{"Device.locked"};
 
-std::string randomString(char minc, char maxc, int len)
-{
-    std::string str;
-
-    std::random_device rd;
-    std::mt19937 gen(rd());
-    std::uniform_int_distribution<> rndgen{int(minc), int(maxc)};
-
-    for (int i = 0; i < len; i++) {
-        char c = rndgen(gen);
-        str.push_back(c);
-    }
-
-    return str;
-}
-
 }
 
 namespace NetworkManager
@@ -63,7 +46,6 @@ Settings Settings::_instance;
 Settings::Settings()
     : serverAddress()
     , deviceId()
-    , serial()
     , keepAliveTimeout(DEFAULT_KEEPALIVE_SECONDS)
     , saveFileName()
     , loaded(false)
@@ -81,7 +63,6 @@ bool Settings::_load(const std::string& fileName)
 
         serverAddress = properties.get<std::string>(PROPKEY_SERVER_ADDR, std::string{});
         deviceId = properties.get<std::string>(PROPKEY_DUID, std::string{});
-        serial = properties.get<std::string>(PROPKEY_SERIAL, std::string{});
         keepAliveTimeout = std::chrono::milliseconds(properties.get<int>(PROPKEY_KEEPALIVE, DEFAULT_KEEPALIVE_SECONDS));
         lock = properties.get<bool>(PROPKEY_LOCK, false);
         loaded = true;
@@ -95,7 +76,6 @@ bool Settings::_load(const std::string& fileName)
 bool Settings::loadDefaults()
 {
     bool result = _load(defaultConfig);
-    serial = randomString('0', '9', 16);
     return result;
 }
 
@@ -122,7 +102,6 @@ bool Settings::save() const
         properties.put(PROPKEY_SERVER_ADDR, serverAddress);
         properties.put(PROPKEY_KEEPALIVE, keepAliveTimeout.count());
         properties.put(PROPKEY_DUID, deviceId);
-        properties.put(PROPKEY_SERIAL, serial);
         properties.put(PROPKEY_LOCK, lock);
 
         boost::property_tree::write_ini(saveFileName, properties);
index 3a101ab..ad05edc 100644 (file)
@@ -108,4 +108,13 @@ std::string SysInfo::swVersion()
     return prop;
 }
 
+std::string SysInfo::tizenId()
+{
+    std::string prop;
+    if (!getStringPlatformProperty("tizen.org/system/tizenid", prop)) {
+        prop = UNDEFINED_VAL;
+    }
+    return prop;
+}
+
 }
index ba45ba1..d669c0b 100644 (file)
@@ -19,6 +19,7 @@
 #include "main_thread.h"
 #include "utils.h"
 #include "policyhandler.h"
+#include "policystatehandler.h"
 #include "proxythread.h"
 #include "audit_trail_client.h"
 #include "application_service.h"
@@ -71,6 +72,7 @@ void MainThread::routine()
         NetworkManager::Connection conn(settings, &rest);
 
         PolicyHandler policy_handler(conn);
+        PolicyStateHandler policy_state_handler(conn);
         ReportAdapter report_adapter(conn);
         SettingsHandler settings_handler(conn);
         std::shared_ptr<AuditTrailClient> audit_trail_client = nullptr;
index b6423b0..c1d1722 100644 (file)
@@ -26,7 +26,7 @@ public:
 
     /**
      * @brief Constructor
-     * @param iotivity pointer to the IoTivity instance
+     * @param conn a connection to assosiate
      */
     PolicyHandler(NetworkManager::Connection& conn);
 
diff --git a/device-agent/daemon/policystatehandler.cpp b/device-agent/daemon/policystatehandler.cpp
new file mode 100644 (file)
index 0000000..f6d924a
--- /dev/null
@@ -0,0 +1,33 @@
+#include "policystatehandler.h"
+#include "policy_enforce.h"
+#include <jsoncpp/json/reader.h>
+
+const std::string PolicyStateHandler::EVENT_TYPE{"state-policy"};
+
+PolicyStateHandler::PolicyStateHandler(NetworkManager::Connection& conn):
+    NetworkManager::EventListener(conn, EVENT_TYPE)
+{
+
+}
+
+void PolicyStateHandler::accept(NetworkManager::Event &event)
+{
+    if (NetworkManager::Settings::instance().isLocked()) {
+        return;
+    }
+
+    const std::string& content = event.getContent();
+    Json::Reader reader;
+    Json::Value object;
+
+    if (!content.empty()) {
+        reader.parse(content, object);
+        dpm::PolicyEnforce::Result result = dpm::PolicyEnforce::GetInstance().getStates(object);
+
+        if (dpm::PolicyEnforce::Result::SUCCESS == result) {
+            connection.sendData(object);
+        }
+    }
+
+    event.confirm();
+}
diff --git a/device-agent/daemon/policystatehandler.h b/device-agent/daemon/policystatehandler.h
new file mode 100644 (file)
index 0000000..6964cd6
--- /dev/null
@@ -0,0 +1,34 @@
+/**
+ * Samsung Ukraine R&D Center (SRK under a contract between)
+ * LLC "Samsung Electronics Co", Ltd (Seoul, Republic of Korea)
+ * Copyright (C) 2017 Samsung Electronics Co., Ltd. All rights reserved.
+ */
+/**
+ * @file   policystatehandler.h
+ * @brief  Class for handling policy state query requests
+ * @date   Created Mar 26, 2018
+ * @author Mail to: <A HREF="mailto:d.lomtev@samsung.com">Dmytro Lomtiev, d.lomtev@samsung.com</A>
+ */
+#ifndef POLICYSTATEHANDLER_H
+#define POLICYSTATEHANDLER_H
+
+#include "eventlistener.h"
+
+/**
+ * @brief Class for handling policy state query requests
+ */
+class PolicyStateHandler: public NetworkManager::EventListener
+{
+public:
+    static const std::string EVENT_TYPE;
+
+    /**
+     * @brief Constructor
+     * @param conn a connection to assosiate
+     */
+    PolicyStateHandler(NetworkManager::Connection& conn);
+
+    void accept(NetworkManager::Event& event) override;
+};
+
+#endif // POLICYSTATEHANDLER_H
index 770f94d..c761edf 100644 (file)
@@ -27,8 +27,8 @@ public:
     MOCK_METHOD2(auth, std::string(const SessionInfo& info, const std::string& secret));
     MOCK_METHOD2(doGet, std::string(const SessionInfo& info, const std::string& uri));
     MOCK_METHOD3(doPost, void(const SessionInfo& info, const std::string& uri, const std::string& data));
-    MOCK_METHOD2(sendReport, void(const SessionInfo& info, const std::string& report));
-    MOCK_METHOD2(sendReport, void(const SessionInfo& info, const Json::Value& report));
+    MOCK_METHOD2(sendData, void(const SessionInfo& info, const std::string& report));
+    MOCK_METHOD2(sendData, void(const SessionInfo& info, const Json::Value& report));
 };
 
 }
index 2814792..7323064 100644 (file)
@@ -91,7 +91,7 @@ TEST_F(TestConnection, test_signal)
             .WillOnce(Return(TEST_DEVICE_ID));
     EXPECT_CALL(rest, getUpdates(_))
             .WillRepeatedly(Return(""));
-    EXPECT_CALL(rest, sendReport(_, ::testing::Matcher<const Json::Value&>(rc.get())))
+    EXPECT_CALL(rest, sendData(_, ::testing::Matcher<const Json::Value&>(rc.get())))
             .Times(1);
 
     std::thread t(&Connection::loop, &conn);
index e4da1bb..cfad7f4 100644 (file)
@@ -19,8 +19,7 @@ const std::string DEFAULT_UNKNOWN{"unknown"};
 const std::chrono::milliseconds DEFAULT_KEEPALIVE(10);
 
 const std::string DEVICE_ID{"device-id"};
-const std::string DEVICE_SERIAL{"device-serial"};
-const std::string SERVER_ADDRESS{"device-id"};
+const std::string SERVER_ADDRESS{"server-addr"};
 const bool DEVICE_LOCK = true;
 const std::chrono::milliseconds KEEPALIVE_TIME(123);
 
@@ -54,7 +53,6 @@ std::string createSettingsFile()
        << "keepalive=" << KEEPALIVE_TIME.count() << std::endl
        << "[Device]" << std::endl
        << "id=" << DEVICE_ID << std::endl
-       << "serial=" << DEVICE_SERIAL << std::endl
        << "locked=" << int(DEVICE_LOCK) << std::endl;
     return filename;
 }
@@ -82,22 +80,13 @@ public:
 TEST_F(TestSettings, test_Constructors)
 {
     Settings& settings = Settings::instance();
-
-//    ASSERT_TRUE(settings.getServerAddress().empty());
-//    ASSERT_TRUE(settings.getDeviceId().empty());
-//    ASSERT_TRUE(settings.getSerial().empty());
-//    ASSERT_FALSE(settings.isLoaded());
-//    ASSERT_EQ(DEFAULT_KEEPALIVE, settings.getKeepAliveTimeout());
-
     std::string filename = createSettingsFile();
-//    Settings from_ini(filename);
     settings.setSaveFileName(filename);
     EXPECT_TRUE(settings.load());
 
     EXPECT_TRUE(settings.isLoaded());
     EXPECT_EQ(SERVER_ADDRESS, settings.getServerAddress());
     EXPECT_EQ(DEVICE_ID, settings.getDeviceId());
-    EXPECT_EQ(DEVICE_SERIAL, settings.getSerial());
     EXPECT_EQ(KEEPALIVE_TIME, settings.getKeepAliveTimeout());
     EXPECT_EQ(DEVICE_LOCK, settings.isLocked());
 
@@ -154,8 +143,6 @@ TEST_F(TestSettings, test_save)
     std::string rnd_addr = randomString('a', 'z', 10);
     settings.setServerAddress(rnd_addr);
 
-    std::string serial = settings.getSerial();
-
     std::chrono::milliseconds timeout(333);
     settings.setKeepAliveTimeout(timeout);
 
@@ -180,7 +167,6 @@ TEST_F(TestSettings, test_save)
 
     ASSERT_EQ(rnd_duid, settings.getDeviceId());
     ASSERT_EQ(timeout, settings.getKeepAliveTimeout());
-    ASSERT_EQ(serial, settings.getSerial());
     ASSERT_EQ(rnd_addr, settings.getServerAddress());
     ASSERT_TRUE(settings.isLocked());
 }