#include <klay/filesystem.h>
+#include <algorithm>
+
namespace vist {
namespace policy {
const PolicyValue& value,
const std::string& admin)
{
- if (this->policies.find(policy) == this->policies.end())
- THROW(ErrCode::RuntimeError) << "Not exist policy: " << policy;
-
this->storage.update(admin, policy, value);
-
- for (auto& p : providers) {
- if (p->getName() != this->policies[policy])
- continue;
-
- /// dispatch callback written by provider
- if (p->policies.find(policy) != p->policies.end()) {
- p->policies[policy]->set(value);
- return;
- }
- }
+ this->getPolicy(policy)->set(value);
}
PolicyValue PolicyManager::get(const std::string& policy)
{
- if (this->policies.find(policy) == this->policies.end())
- THROW(ErrCode::RuntimeError) << "Not exist policy: " << policy;
-
- return storage.strictest(policy);
+ return storage.strictest(this->getPolicy(policy));
}
std::unordered_map<std::string, PolicyValue> PolicyManager::getAll()
{
- return storage.strictest();
+ std::unordered_map<std::string, PolicyValue> policies;
+ for (const auto& pair : this->policies) {
+ std::string policyName = pair.first;
+ auto value = this->get(policyName);
+
+ policies.emplace(std::move(policyName), std::move(value));
+ }
+
+ return policies;
}
std::vector<std::string> PolicyManager::getAdmins()
return storage.getAdmins();
}
+const std::shared_ptr<PolicyModel>& PolicyManager::getPolicy(const std::string& name)
+{
+ if (this->policies.find(name) == this->policies.end())
+ THROW(ErrCode::RuntimeError) << "Not exist policy: " << name;
+
+ auto provider = this->policies[name];
+ auto iter = std::find_if(this->providers.begin(), this->providers.end(),
+ [&provider](const std::unique_ptr<PolicyProvider>& p) {
+ return p->getName() == provider;
+ });
+ if (iter == this->providers.end())
+ THROW(ErrCode::RuntimeError) << "Not exist provider[" << provider
+ << "] about policy: " << name;
+
+ return (*iter)->policies[name];
+}
+
} // namespace policy
} // namespace vist
PolicyStorage storage;
std::vector<std::unique_ptr<PolicyProvider>> providers;
+ const std::shared_ptr<PolicyModel>& getPolicy(const std::string& name);
+
/// Policy-Provider
std::unordered_map<std::string, std::string> policies;
FRIEND_TEST(PolicyCoreTests, policy_loader);
+ FRIEND_TEST(PolicyCoreTests, policy_get_policy);
};
} // namespace policy
/// TODO(sangwan.kwon) Re-design strictest logic
/// PolicyValue PolicyStorage::strictest(const PolicyValue& policy)
-PolicyValue PolicyStorage::strictest(const std::string& policy)
+PolicyValue PolicyStorage::strictest(const std::shared_ptr<PolicyModel>& policy)
{
- if (this->definitions.find(policy) == this->definitions.end())
- THROW(ErrCode::LogicError) << "Not exist policy: " << policy;
+ if (this->definitions.find(policy->getName()) == this->definitions.end())
+ THROW(ErrCode::LogicError) << "Not exist policy: " << policy->getName();
- /// There is no enrolled admins.
- /// Make PolicyValue by dumped string.
- if (this->activatedPolicies.size() == 0)
- return PolicyValue(definitions[policy].ivalue, true);
+ if (this->activatedPolicies.size() == 0) {
+ INFO(VIST) << "There is no enrolled admin. Return policy initial value.";
+ return policy->getInitial();
+ }
std::shared_ptr<PolicyValue> strictestPtr = nullptr;
- auto range = activatedPolicies.equal_range(policy);
+ auto range = activatedPolicies.equal_range(policy->getName());
for (auto iter = range.first; iter != range.second; iter++) {
DEBUG(VIST) << "Admin: " << iter->second.admin << ", "
<< "Policy: " << iter->second.policy << ", "
if (strictestPtr == nullptr) {
strictestPtr = std::make_shared<PolicyValue>(iter->second.value, true);
} else {
- /// TODO: Support String type
- int strictestValue = *strictestPtr;
- if (strictestValue < PolicyValue(iter->second.value, true))
+ if (policy->compare(*strictestPtr, PolicyValue(iter->second.value, true)) > 0)
strictestPtr.reset(new PolicyValue(iter->second.value, true));
}
}
if (strictestPtr == nullptr)
THROW(ErrCode::RuntimeError) << "Not exist managed policy: " << policy;
- int strictestValue = *strictestPtr;
- DEBUG(VIST) << "The strictest value of [" << policy
- << "] is " << strictestValue;
+ DEBUG(VIST) << "The strictest value of [" << policy->getName()
+ << "] is " << strictestPtr->dump();
return std::move(*strictestPtr);
}
-std::unordered_map<std::string, PolicyValue> PolicyStorage::strictest()
-{
- std::unordered_map<std::string, PolicyValue> policies;
- for (const auto& pair : definitions) {
- std::string name = pair.first;
- auto value = this->strictest(name);
-
- policies.emplace(std::move(name), std::move(value));
- }
-
- return policies;
-}
-
const std::vector<std::string>& PolicyStorage::getAdmins() const noexcept
{
return admins;
#pragma once
+#include <vist/sdk/policy-model.hpp>
#include <vist/sdk/policy-value.hpp>
#include "db-schema.hpp"
const std::string& policy,
const PolicyValue& value);
- PolicyValue strictest(const std::string& policy);
- /// Return all strictest policy values
- std::unordered_map<std::string, PolicyValue> strictest();
+ PolicyValue strictest(const std::shared_ptr<PolicyModel>& policy);
const std::vector<std::string>& getAdmins() const noexcept;
namespace vist {
namespace policy {
-class PolicyCoreTests : public testing::Test {};
-
-TEST_F(PolicyCoreTests, policy_loader) {
+TEST(PolicyCoreTests, policy_loader) {
auto& manager = PolicyManager::Instance();
EXPECT_TRUE(manager.providers.size() > 0);
EXPECT_TRUE(manager.policies.size() > 0);
}
-TEST_F(PolicyCoreTests, policy_set_get) {
+TEST(PolicyCoreTests, policy_set_get) {
auto& manager = PolicyManager::Instance();
manager.enroll("testAdmin");
manager.set("bluetooth", PolicyValue(5), "testAdmin");
auto policy = manager.get("bluetooth");
- EXPECT_EQ((int)policy, 5);
+ EXPECT_EQ(static_cast<int>(policy), 5);
manager.enroll("testAdmin1");
manager.set("bluetooth", PolicyValue(10), "testAdmin1");
/// Manager should return the strongest policy.
policy = manager.get("bluetooth");
- EXPECT_EQ((int)policy, 10);
+ EXPECT_EQ(static_cast<int>(policy), 10);
manager.disenroll("testAdmin");
manager.disenroll("testAdmin1");
}
+TEST(PolicyCoreTests, policy_get_all) {
+ auto& manager = PolicyManager::Instance();
+ auto policies = manager.getAll();
+ EXPECT_TRUE(policies.size() > 0);
+}
+
+TEST(PolicyCoreTests, policy_get_policy) {
+ auto& manager = PolicyManager::Instance();
+ const auto& policy = manager.getPolicy("bluetooth");
+ EXPECT_EQ(policy->getName(), "bluetooth");
+
+ bool raised = false;
+ try {
+ manager.getPolicy("fakePolicy");
+ } catch (const vist::Exception<ErrCode>&) {
+ raised = true;
+ }
+ EXPECT_TRUE(raised);
+}
+
} // namespace policy
} // namespace vist
storage->disenroll("testAdmin");
}
-TEST_F(PolicyStorageTests, strictest)
-{
- auto storage = getStorage();
- storage->enroll("testAdmin0");
- storage->enroll("testAdmin1");
-
- storage->update("testAdmin0", "bluetooth", PolicyValue(3));
- storage->update("testAdmin1", "bluetooth", PolicyValue(6));
-
- bool isRaised = false;
- try {
- auto value = storage->strictest("FakePolicy");
- } catch (const std::exception&) {
- isRaised = true;
- }
- EXPECT_TRUE(isRaised);
-
- auto policy = storage->strictest("bluetooth");
- EXPECT_EQ((int)policy, 6);
-
- storage->disenroll("testAdmin0");
- storage->disenroll("testAdmin1");
-}
-
-TEST_F(PolicyStorageTests, strictest_all)
-{
- auto storage = getStorage();
- storage->enroll("testAdmin");
-
- auto policies = storage->strictest();
- EXPECT_TRUE(policies.size() > 0);
-
- storage->disenroll("testAdmin");
-}
-
TEST_F(PolicyStorageTests, admin_list)
{
auto storage = getStorage();
return current;
}
+ /// Default compare function for int type
+ virtual int compare(const PolicyValue& lhs, const PolicyValue& rhs) const
+ {
+ int lvalue = lhs;
+ int rvalue = rhs;
+
+ if (lvalue < rvalue)
+ return 1;
+ else if (lvalue == rvalue)
+ return 0;
+ else
+ return -1;
+ }
+
virtual void onChanged(const PolicyValue& value) = 0;
const std::string& getName() const noexcept { return name; }