Add CustomPublisher 76/141076/4
authorMu-Woong Lee <muwoong.lee@samsung.com>
Fri, 28 Jul 2017 04:55:09 +0000 (13:55 +0900)
committerMu-Woong Lee <muwoong.lee@samsung.com>
Fri, 28 Jul 2017 06:08:04 +0000 (15:08 +0900)
Change-Id: I8a100d8298bef247e56b66c2768b83e621abb46b
Signed-off-by: Mu-Woong Lee <muwoong.lee@samsung.com>
15 files changed:
include/job_scheduler_internal.h
src/client-dummy/job_scheduler.cpp
src/client/JobManagerProxy.cpp
src/client/JobManagerProxy.h
src/client/job_scheduler.cpp
src/server/ContextManager.cpp
src/server/ContextManager.h
src/server/ContextPublisher.cpp
src/server/ContextPublisher.h
src/server/JobManager.cpp
src/server/MethodCallHandler.cpp
src/server/MethodCallHandler.h
src/server/publisher/CustomPublisher.cpp [new file with mode: 0644]
src/server/publisher/CustomPublisher.h [new file with mode: 0644]
src/shared/JobSchedulerTypesPrivate.h

index 91f1fac1040c9bc0daac1baf3cc7d41d08c7fa5a..094f10b5e8d2605c67d32eb0ba0104543a479927 100644 (file)
@@ -491,22 +491,6 @@ int ctx_sched_job_context_attribute_set_le_int(ctx_sched_job_context_h job_conte
 int ctx_sched_job_context_destroy(ctx_sched_job_context_h job_context);
 
 
-/**
- * @brief      Declares a custom context that can be used as a trigger or a requirement by other applications.
- * @param[in]  scheduler       TBD
- * @param[in]  uri                     TBD
- * @return     @c 0 on success, otherwise a negative error value
- */
-int ctx_sched_declare_context(ctx_sched_h scheduler, const char* uri);
-
-/**
- * @brief      Retracts a custom context declared by the current application.
- * @param[in]  scheduler       TBD
- * @param[in]  uri                     TBD
- * @return     @c 0 on success, otherwise a negative error value
- */
-int ctx_sched_undeclare_context(ctx_sched_h scheduler, const char* uri);
-
 /**
  * @brief      Publishes a custom context data corresponding to a URI declared using ctx_sched_declare_context().
  * @param[in]  scheduler               TBD
index 0b434517cf31026e7dd284cbb1a189229d1303b0..53c373f7cff7081d8a0aa879d9de7b9ef69ba945 100644 (file)
@@ -252,16 +252,6 @@ EXPORT_API int ctx_sched_job_context_destroy(ctx_sched_job_context_h job_context
        return E_SUPPORT;
 }
 
-EXPORT_API int ctx_sched_declare_context(ctx_sched_h scheduler, const char* uri)
-{
-       return E_SUPPORT;
-}
-
-EXPORT_API int ctx_sched_undeclare_context(ctx_sched_h scheduler, const char* uri)
-{
-       return E_SUPPORT;
-}
-
 EXPORT_API int ctx_sched_publish_context_json(ctx_sched_h scheduler, const char* uri, const char* json_payload)
 {
        return E_SUPPORT;
index 6df8179b5bc28c697af3772b8eb7992e61a2f4f1..54200f0d031941f2c95b590759c3a1c4cfc784a1 100644 (file)
@@ -175,6 +175,11 @@ bool JobManagerProxy::isAvailableRequirement(const std::string& uri)
        return __isAvailable(static_cast<int>(JobContext::Type::REQUIREMENT), uri);
 }
 
+int JobManagerProxy::publishContext(const std::string& uri, const std::string& payload)
+{
+       return __serviceProxy.call(METHOD_PUBLISH_CONTEXT, g_variant_new("(ss)", uri.c_str(), payload.c_str()));
+}
+
 bool JobManagerProxy::__isAvailable(int type, const std::string& uri)
 {
        GVariant* param = g_variant_new("(is)", type, uri.c_str());
index 5c9d34a2575453d36828ea61ac6df520aa46d8fc..d069a16ed9877a1fd81f3c804a90305c4f471d6d 100644 (file)
@@ -48,6 +48,8 @@ namespace ctx {
                bool isAvailableTrigger(const std::string& uri);
                bool isAvailableRequirement(const std::string& uri);
 
+               int publishContext(const std::string& uri, const std::string& payload);
+
        private:
                bool __isAvailable(int type, const std::string& uri);
                void __onStartJob(GVariant* param);
index 21afc464bee595297708503e4d786756dc2cf2db..ffe4cdf5ab363048382e4de548bf71b72792799a 100644 (file)
@@ -643,25 +643,11 @@ EXPORT_API int ctx_sched_job_context_destroy(ctx_sched_job_context_h job_context
        return E_NONE;
 }
 
-EXPORT_API int ctx_sched_declare_context(ctx_sched_h scheduler, const char* uri)
-{
-       IF_FAIL_RETURN(scheduler && uri, E_PARAM);
-       //TODO
-       return E_SUPPORT;
-}
-
-EXPORT_API int ctx_sched_undeclare_context(ctx_sched_h scheduler, const char* uri)
-{
-       IF_FAIL_RETURN(scheduler && uri, E_PARAM);
-       //TODO
-       return E_SUPPORT;
-}
-
 EXPORT_API int ctx_sched_publish_context_json(ctx_sched_h scheduler, const char* uri, const char* json_payload)
 {
        IF_FAIL_RETURN(scheduler && uri && json_payload, E_PARAM);
-       //TODO
-       return E_SUPPORT;
+
+       return scheduler->jobManager.publishContext(uri, json_payload);
 }
 
 EXPORT_API int ctx_sched_job_set_disjunction(ctx_sched_job_h job, bool disjunction)
index 7f6f27c113322cd45ddf85f32bfcb15705d9c17e..c8c012197e9a29ce00f2ec9fa8c3315747520313 100644 (file)
@@ -52,14 +52,19 @@ ContextPublisher* ContextManager::getPublisher(const std::string& uri, uid_t uid
        return __instance->__getPublisher(uri.c_str(), uid);
 }
 
+bool ContextManager::isCustomUri(const std::string& uri)
+{
+       return ContextPublisher::isCustomUri(uri);
+}
+
 ContextPublisher* ContextManager::__getPublisher(const char* uri, uid_t uid)
 {
        ContextPublisher* pubs = NULL;
 
-       if ((pubs = __find(uri, SYSTEM_UID)))
+       if ((pubs = __find(uri, uid)))
                return pubs;
 
-       if ((pubs = __find(uri, uid)))
+       if ((pubs = __find(uri, SYSTEM_UID)))
                return pubs;
 
        try {
index 5ae8f2688b4e23f737ddd709df05b1a78570b7aa..33a2da4b21cacbaa1f2fe5f9188875b8ab5b241d 100644 (file)
@@ -31,6 +31,7 @@ namespace ctx {
                static void init();
                static void release();
                static ContextPublisher* getPublisher(const std::string& uri, uid_t uid);
+               static bool isCustomUri(const std::string& uri);
 
        private:
                ContextManager();
index b19e1f0c3e8b18fd5af13c5b9736ce24e15f6175..f25fff0acb6b993d8829a74c7d8b4786d0b03a9e 100644 (file)
  */
 
 #include <vector>
+#include <regex>
 #include <ContextTypes.h>
 #include <SharedUtil.h>
 #include "IContextObserver.h"
 #include "ContextPublisher.h"
+#include "publisher/CustomPublisher.h"
+
+#define CUSTOM_URI_REGEX       R"~(^http:\/\/[\w-\.]+\/context\/custom\/[\w-\._]+$)~"
 
 using namespace ctx;
 
@@ -31,13 +35,22 @@ void ContextPublisher::registerPublisher(const char* uri, ContextPublisher* (*cr
 
 ContextPublisher* ContextPublisher::build(const char* uri, uid_t uid)
 {
+       // Pre-defined publishers
        for (auto& it : __creators) {
                if (STR_EQ(it.first, uri)) {
                        return (it.second)(uid);
                }
        }
 
-       throw E_SUPPORT;
+       // Custom publishers
+       IF_FAIL_THROW(isCustomUri(uri), E_SUPPORT);
+       return new CustomPublisher(uri, uid);
+}
+
+bool ContextPublisher::isCustomUri(const std::string& uri)
+{
+       static std::regex customUriRegex(CUSTOM_URI_REGEX, std::regex::optimize);
+       return std::regex_match(uri, customUriRegex);
 }
 
 ContextPublisher::~ContextPublisher()
@@ -83,6 +96,12 @@ bool ContextPublisher::isReadable() const
        return true;
 }
 
+bool ContextPublisher::isWritable() const
+{
+       // Pre-defined context items are not allowed to be written by clients.
+       return false;
+}
+
 bool ContextPublisher::isUserContext() const
 {
        // Most context items are system-level data.
@@ -99,6 +118,11 @@ const Json::Value& ContextPublisher::getData()
        return __data;
 }
 
+void ContextPublisher::putData(const Json::Value& data)
+{
+       // Pre-defined publishers do not support this.
+}
+
 void ContextPublisher::notifyObservers()
 {
        _D("%s notifies", getUri());
index 937b7803587688c2efa0ce16e1d48077e5be21f5..b76ca6b09e05e87e14f72244d878e35390ac64fd 100644 (file)
@@ -44,15 +44,20 @@ namespace ctx {
                virtual const char* getUri() const = 0;
                virtual const char* getPrivilege() const;
 
+               // If not readable, it cannot be used as a requirement
                virtual bool isReadable() const;
+               virtual bool isWritable() const;
                virtual bool isUserContext() const;
 
                virtual bool isReady();
                virtual const Json::Value& getData();
+               virtual void putData(const Json::Value& data);
 
                static void registerPublisher(const char* uri, ContextPublisher* (*creator)(uid_t));
                static ContextPublisher* build(const char* uri, uid_t uid);
 
+               static bool isCustomUri(const std::string& uri);
+
        protected:
                void notifyObservers();
 
index 478f62a09b231f28322b242a2ebd4ee03d03fe0d..1952a43fa1bf51fd81028399c8db098d16e1e92b 100644 (file)
@@ -96,6 +96,9 @@ uid_t JobManager::getUid() const
 
 bool JobManager::isSupported(JobContext::Type type, const std::string& uri, IClient* client)
 {
+       if (ContextManager::isCustomUri(uri))
+               return true;
+
        ContextPublisher* pubs = ContextManager::getPublisher(uri, client->getUid());
        IF_FAIL_RETURN(pubs, false);
 
@@ -294,9 +297,13 @@ JobInfo* JobManager::__getDuplicate(const std::string& ownerId, JobInfo* target)
 
 bool JobManager::__isPermitted(const std::string& uri, IClient* client)
 {
+       if (ContextManager::isCustomUri(uri))
+               return true;
+
        ContextPublisher* pubs = ContextManager::getPublisher(uri, client->getUid());
        IF_FAIL_RETURN(pubs, false);
        IF_FAIL_RETURN(client->hasPrivilege(pubs->getPrivilege()), false);
+
        return true;
 }
 
index 4bdf7aacd9885f99d60981e693fe22ed29efb16d..eeebeea23d24ba3df82ac62ea78f8673ac7c3472 100644 (file)
  */
 
 #include <algorithm>
+#include <json/json.h>
 #include <JobSchedulerTypesPrivate.h>
 #include <JobSchedulerService.h>
 #include "JobManager.h"
+#include "ContextManager.h"
+#include "ContextPublisher.h"
 #include "MethodCallHandler.h"
 
 using namespace ctx;
@@ -61,6 +64,9 @@ void MethodCallHandler::onMethodCalled(IMethodCall* methodCall)
 
                } else if (methodCall->getMethodName() == METHOD_ENABLE_CB) {
                        __enableLifecycleCallbacks(*methodCall);
+
+               } else if (methodCall->getMethodName() == METHOD_PUBLISH_CONTEXT) {
+                       __publishContext(*methodCall);
                }
        } catch (const int error) {
                _W("Catch: %s", CTX_ERROR_STR(error));
@@ -227,3 +233,29 @@ void MethodCallHandler::__enableLifecycleCallbacks(IMethodCall& methodCall)
 
        methodCall.reply(E_NONE);
 }
+
+void MethodCallHandler::__publishContext(IMethodCall& methodCall)
+{
+       const char* uri = NULL;
+       const char* payload = NULL;
+       Json::Value data;
+
+       g_variant_get(methodCall.getParam(), "(&s&s)", &uri, &payload);
+       IF_FAIL_THROW(uri && payload, E_PARAM);
+
+       try {
+               Json::Reader reader;
+               reader.parse(payload, data);
+       } catch (const Json::Exception& e) {
+               _E("Exception: %s", e.what());
+               throw E_PARAM;
+       }
+
+       ContextPublisher* pubs = ContextManager::getPublisher(uri, __caller->getUid());
+       IF_FAIL_THROW(pubs, E_PARAM);
+       IF_FAIL_THROW(pubs->isWritable(), E_PARAM);
+
+       methodCall.reply(E_NONE);
+
+       pubs->putData(data);
+}
index 4098745dc9a8a0f1def785a7c67382c0170e43aa..e2432037569c4fab2c3d486e307c0eb13869c339 100644 (file)
@@ -45,6 +45,7 @@ namespace ctx {
                void __getJob(IMethodCall& methodCall);
                void __getAllJob(IMethodCall& methodCall);
                void __enableLifecycleCallbacks(IMethodCall& methodCall);
+               void __publishContext(IMethodCall& methodCall);
 
                IClient* __caller;
                bool __callbackEnabled;
diff --git a/src/server/publisher/CustomPublisher.cpp b/src/server/publisher/CustomPublisher.cpp
new file mode 100644 (file)
index 0000000..8ed7b70
--- /dev/null
@@ -0,0 +1,78 @@
+/*
+ * Copyright (c) 2017 Samsung Electronics Co., Ltd.
+ *
+ * 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 <ContextTypes.h>
+#include <JobSchedulerTypesPrivate.h>
+#include <job_scheduler_types_internal.h>
+#include "CustomPublisher.h"
+#include "../IContextObserver.h"
+
+using namespace ctx;
+
+CustomPublisher::CustomPublisher(const std::string& uri, uid_t uid) :
+       __uri(uri),
+       __uid(uid)
+{
+       _D("Created '%s' (%u)", __uri.c_str(), static_cast<unsigned>(__uid));
+}
+
+CustomPublisher::~CustomPublisher()
+{
+       _D("Destroyed '%s' (%u)", __uri.c_str(), static_cast<unsigned>(__uid));
+}
+
+const char* CustomPublisher::getUri() const
+{
+       return __uri.c_str();
+}
+
+bool CustomPublisher::isWritable() const
+{
+       return true;
+}
+
+bool CustomPublisher::isUserContext() const
+{
+       return true;
+}
+
+void CustomPublisher::putData(const Json::Value& data)
+{
+       _D("Publish '%s' (%u)", __uri.c_str(), static_cast<unsigned>(__uid));
+       __data = data;
+       notifyObservers();
+}
+
+void CustomPublisher::read()
+{
+       // CustomPublisher works passively.
+}
+
+void CustomPublisher::subscribe()
+{
+       // CustomPublisher works passively.
+}
+
+void CustomPublisher::unsubscribe()
+{
+       // CustomPublisher works passively.
+}
+
+void CustomPublisher::clearData()
+{
+       // CustomPublisher cannot read data from its source.
+       // The cached should not be removed.
+}
diff --git a/src/server/publisher/CustomPublisher.h b/src/server/publisher/CustomPublisher.h
new file mode 100644 (file)
index 0000000..f91a71d
--- /dev/null
@@ -0,0 +1,50 @@
+/*
+ * Copyright (c) 2017 Samsung Electronics Co., Ltd.
+ *
+ * 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.
+ */
+
+#ifndef __CONTEXT_JOB_SCHEDULER_CUSTOM_PUBLISHER_H__
+#define __CONTEXT_JOB_SCHEDULER_CUSTOM_PUBLISHER_H__
+
+#include <string>
+#include "../ContextPublisher.h"
+
+namespace ctx {
+
+       class CustomPublisher : public ContextPublisher {
+       public:
+               CustomPublisher(const std::string& uri, uid_t uid);
+               ~CustomPublisher();
+
+               const char* getUri() const;
+
+               bool isWritable() const;
+               bool isUserContext() const;
+
+               void putData(const Json::Value& data);
+
+       protected:
+               void read();
+               void subscribe();
+               void unsubscribe();
+               void clearData();
+
+       private:
+               std::string __uri;
+               uid_t __uid;
+       };
+
+}
+
+#endif /* __CONTEXT_JOB_SCHEDULER_CUSTOM_PUBLISHER_H__ */
index 15b2458747055b405739722379c31b91b108e16a..34e6b69e60b6881a47845a5d5bfc2f6826d38127 100644 (file)
        "<method name='" METHOD_GET_ALL_JOB "'>" \
        "       <arg type='as' name='jobs' direction='out'/>" \
        "</method>" \
-       "<method name='" METHOD_IS_SUPPORTED"'>" \
+       "<method name='" METHOD_IS_SUPPORTED "'>" \
        "       <arg type='i' name='type' direction='in'/>" \
        "       <arg type='s' name='uri' direction='in'/>" \
        "</method>" \
-       "<method name='" METHOD_ENABLE_CB"'>" \
+       "<method name='" METHOD_ENABLE_CB "'/>" \
+       "<method name='" METHOD_PUBLISH_CONTEXT "'>" \
+       "       <arg type='s' name='uri' direction='in'/>" \
+       "       <arg type='s' name='payload' direction='in'/>" \
        "</method>"
 
-#define METHOD_ADD_JOB         "AddJob"
-#define METHOD_START_JOB       "StartJob"
-#define METHOD_STOP_JOB                "StopJob"
-#define METHOD_REMOVE_JOB      "RemoveJob"
-#define METHOD_JOB_FINISHED    "JobFinished"
-#define METHOD_GET_JOB         "GetJob"
-#define METHOD_GET_ALL_JOB     "GetAllJob"
-#define METHOD_IS_SUPPORTED    "IsSupported"
-#define METHOD_ENABLE_CB       "EnableCb"
+#define METHOD_ADD_JOB                 "AddJob"
+#define METHOD_START_JOB               "StartJob"
+#define METHOD_STOP_JOB                        "StopJob"
+#define METHOD_REMOVE_JOB              "RemoveJob"
+#define METHOD_JOB_FINISHED            "JobFinished"
+#define METHOD_GET_JOB                 "GetJob"
+#define METHOD_GET_ALL_JOB             "GetAllJob"
+#define METHOD_IS_SUPPORTED            "IsSupported"
+#define METHOD_ENABLE_CB               "EnableCb"
+#define METHOD_PUBLISH_CONTEXT "PublishContext"
 
-#define SIGNAL_START_JOB       "JobStarted"
-#define SIGNAL_STOP_JOB                "JobToBeStopped"
+#define SIGNAL_START_JOB               "JobStarted"
+#define SIGNAL_STOP_JOB                        "JobToBeStopped"
 
 #define URI(x)         CTX_SCHED_URI_##x
 #define NAME(x)                CTX_SCHED_ATTR_NAME_##x