mirror of https://github.com/Icinga/icinga2.git
Fix: Names for nested objects are evaluated at the wrong time
fixes #7689
This commit is contained in:
parent
9635f359e9
commit
3bb79715fa
|
@ -151,11 +151,12 @@ DynamicObject::Ptr ConfigItem::Commit(bool discard)
|
||||||
Dictionary::Ptr locals = new Dictionary();
|
Dictionary::Ptr locals = new Dictionary();
|
||||||
locals->Set("__parent", m_Scope);
|
locals->Set("__parent", m_Scope);
|
||||||
m_Scope.reset();
|
m_Scope.reset();
|
||||||
locals->Set("name", m_Name);
|
|
||||||
|
|
||||||
dobj->SetParentScope(locals);
|
dobj->SetParentScope(locals);
|
||||||
locals.reset();
|
locals.reset();
|
||||||
|
|
||||||
|
dobj->SetName(m_Name);
|
||||||
|
|
||||||
DebugHint debugHints;
|
DebugHint debugHints;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
@ -269,64 +270,72 @@ ConfigItem::Ptr ConfigItem::GetObject(const String& type, const String& name)
|
||||||
return ConfigItem::Ptr();
|
return ConfigItem::Ptr();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool ConfigItem::CommitNewItems(void)
|
||||||
|
{
|
||||||
|
std::vector<ConfigItem::Ptr> items;
|
||||||
|
|
||||||
|
do {
|
||||||
|
ParallelWorkQueue upq;
|
||||||
|
|
||||||
|
items.clear();
|
||||||
|
|
||||||
|
{
|
||||||
|
boost::mutex::scoped_lock lock(m_Mutex);
|
||||||
|
|
||||||
|
BOOST_FOREACH(const ItemMap::value_type& kv, m_Items) {
|
||||||
|
if (!kv.second->m_Abstract && !kv.second->m_Object) {
|
||||||
|
upq.Enqueue(boost::bind(&ConfigItem::Commit, kv.second, false));
|
||||||
|
items.push_back(kv.second);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
BOOST_FOREACH(const ConfigItem::Ptr& item, m_UnnamedItems) {
|
||||||
|
if (!item->m_Abstract && !item->m_Object) {
|
||||||
|
upq.Enqueue(boost::bind(&ConfigItem::Commit, item, true));
|
||||||
|
items.push_back(item);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
m_UnnamedItems.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
upq.Join();
|
||||||
|
|
||||||
|
if (ConfigCompilerContext::GetInstance()->HasErrors())
|
||||||
|
return false;
|
||||||
|
|
||||||
|
BOOST_FOREACH(const ConfigItem::Ptr& item, items) {
|
||||||
|
upq.Enqueue(boost::bind(&DynamicObject::OnConfigLoaded, item->m_Object));
|
||||||
|
}
|
||||||
|
|
||||||
|
upq.Join();
|
||||||
|
} while (!items.empty());
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
bool ConfigItem::ValidateItems(void)
|
bool ConfigItem::ValidateItems(void)
|
||||||
{
|
{
|
||||||
if (ConfigCompilerContext::GetInstance()->HasErrors())
|
if (ConfigCompilerContext::GetInstance()->HasErrors())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
ParallelWorkQueue upq;
|
|
||||||
|
|
||||||
Log(LogInformation, "ConfigItem", "Committing config items");
|
Log(LogInformation, "ConfigItem", "Committing config items");
|
||||||
|
|
||||||
BOOST_FOREACH(const ItemMap::value_type& kv, m_Items) {
|
if (!CommitNewItems())
|
||||||
upq.Enqueue(boost::bind(&ConfigItem::Commit, kv.second, false));
|
|
||||||
}
|
|
||||||
|
|
||||||
BOOST_FOREACH(const ConfigItem::Ptr& item, m_UnnamedItems) {
|
|
||||||
upq.Enqueue(boost::bind(&ConfigItem::Commit, item, true));
|
|
||||||
}
|
|
||||||
|
|
||||||
upq.Join();
|
|
||||||
|
|
||||||
if (ConfigCompilerContext::GetInstance()->HasErrors())
|
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
std::vector<DynamicObject::Ptr> objects;
|
|
||||||
BOOST_FOREACH(const ItemMap::value_type& kv, m_Items) {
|
|
||||||
DynamicObject::Ptr object = kv.second->m_Object;
|
|
||||||
|
|
||||||
if (object)
|
|
||||||
objects.push_back(object);
|
|
||||||
}
|
|
||||||
|
|
||||||
BOOST_FOREACH(const ConfigItem::Ptr& item, m_UnnamedItems) {
|
|
||||||
DynamicObject::Ptr object = item->m_Object;
|
|
||||||
|
|
||||||
if (object)
|
|
||||||
objects.push_back(object);
|
|
||||||
}
|
|
||||||
|
|
||||||
m_UnnamedItems.clear();
|
|
||||||
|
|
||||||
Log(LogInformation, "ConfigItem", "Triggering OnConfigLoaded signal for config items");
|
|
||||||
|
|
||||||
BOOST_FOREACH(const DynamicObject::Ptr& object, objects) {
|
|
||||||
upq.Enqueue(boost::bind(&DynamicObject::OnConfigLoaded, object));
|
|
||||||
}
|
|
||||||
|
|
||||||
upq.Join();
|
|
||||||
|
|
||||||
Log(LogInformation, "ConfigItem", "Evaluating 'object' rules (step 1)...");
|
Log(LogInformation, "ConfigItem", "Evaluating 'object' rules (step 1)...");
|
||||||
ObjectRule::EvaluateRules(false);
|
ObjectRule::EvaluateRules(false);
|
||||||
|
|
||||||
Log(LogInformation, "ConfigItem", "Evaluating 'apply' rules...");
|
Log(LogInformation, "ConfigItem", "Evaluating 'apply' rules...");
|
||||||
ApplyRule::EvaluateRules(true);
|
ApplyRule::EvaluateRules(true);
|
||||||
|
|
||||||
|
if (!CommitNewItems())
|
||||||
|
return false;
|
||||||
|
|
||||||
Log(LogInformation, "ConfigItem", "Evaluating 'object' rules (step 2)...");
|
Log(LogInformation, "ConfigItem", "Evaluating 'object' rules (step 2)...");
|
||||||
ObjectRule::EvaluateRules(true);
|
ObjectRule::EvaluateRules(true);
|
||||||
|
|
||||||
upq.Join();
|
|
||||||
|
|
||||||
ConfigItem::DiscardItems();
|
ConfigItem::DiscardItems();
|
||||||
ConfigType::DiscardTypes();
|
ConfigType::DiscardTypes();
|
||||||
|
|
||||||
|
|
|
@ -87,6 +87,8 @@ private:
|
||||||
|
|
||||||
static ConfigItem::Ptr GetObjectUnlocked(const String& type,
|
static ConfigItem::Ptr GetObjectUnlocked(const String& type,
|
||||||
const String& name);
|
const String& name);
|
||||||
|
|
||||||
|
static bool CommitNewItems(void);
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -115,7 +115,7 @@ void ConfigType::ValidateDictionary(const Dictionary::Ptr& dictionary,
|
||||||
|
|
||||||
Value value = dictionary->Get(require);
|
Value value = dictionary->Get(require);
|
||||||
|
|
||||||
if (value.IsEmpty()) {
|
if (value.IsEmpty() || (value.IsString() && static_cast<String>(value).IsEmpty())) {
|
||||||
ConfigCompilerContext::GetInstance()->AddMessage(true,
|
ConfigCompilerContext::GetInstance()->AddMessage(true,
|
||||||
"Required attribute is missing: " + LocationToString(locations));
|
"Required attribute is missing: " + LocationToString(locations));
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue