diff --git a/doc/18-library-reference.md b/doc/18-library-reference.md
index 9ec4acd31..490497b4a 100644
--- a/doc/18-library-reference.md
+++ b/doc/18-library-reference.md
@@ -908,6 +908,58 @@ function get_objects(type);
Returns an array of objects whose type matches the specified type. `type` must refer
to a type object.
+### get_template
+
+Signature:
+
+```
+function get_template(type, name);
+```
+
+Returns the template with the specified type and name, or `null` if no such object exists. `type` must refer
+to a type object.
+
+> **Note**
+>
+> Only the name and debug info attributes are available for templates accessed in the DSL.
+> Object attributes are not available in this scope.
+
+You can use this functionality to check whether a template exists e.g. on a satellite endpoint
+and if not, import a different template.
+
+```
+object Host "icinga-agent47.localdomain" {
+ if (get_template(Host, "master-host-tmpl")) {
+ import "master-host-tmpl"
+ } else {
+ import "generic-host"
+ }
+}
+```
+
+### get_templates
+
+Signature:
+
+```
+function get_templates(type);
+```
+
+Returns an array of templates whose type matches the specified type. `type` must refer
+to a type object.
+
+> **Note**
+>
+> Only the name and debug info attributes are available for templates accessed in the DSL.
+> Object attributes are not available in this scope.
+
+You can use this function to iterate over all available template names, similar to what
+the [templates API URL endpoint](12-icinga2-api.md#icinga2-api-config-templates) provides.
+
+```
+<1> => get_templates(Host).map(n => n.name)
+[ "ssh-agent" ]
+```
## Math object
diff --git a/lib/base/scriptutils.cpp b/lib/base/scriptutils.cpp
index 47f2ccdea..838f20edd 100644
--- a/lib/base/scriptutils.cpp
+++ b/lib/base/scriptutils.cpp
@@ -14,6 +14,7 @@
#include "base/dependencygraph.hpp"
#include "base/initialize.hpp"
#include "base/namespace.hpp"
+#include "config/configitem.hpp"
#include
#include
#include
@@ -35,6 +36,8 @@ REGISTER_FUNCTION(System, exit, &Application::Exit, "status");
REGISTER_SAFE_FUNCTION(System, typeof, &ScriptUtils::TypeOf, "value");
REGISTER_SAFE_FUNCTION(System, keys, &ScriptUtils::Keys, "value");
REGISTER_SAFE_FUNCTION(System, random, &Utility::Random, "");
+REGISTER_SAFE_FUNCTION(System, get_template, &ScriptUtils::GetTemplate, "type:name");
+REGISTER_SAFE_FUNCTION(System, get_templates, &ScriptUtils::GetTemplates, "type");
REGISTER_SAFE_FUNCTION(System, get_object, &ScriptUtils::GetObject, "type:name");
REGISTER_SAFE_FUNCTION(System, get_objects, &ScriptUtils::GetObjects, "type");
REGISTER_FUNCTION(System, assert, &ScriptUtils::Assert, "value");
@@ -407,6 +410,57 @@ Array::Ptr ScriptUtils::Keys(const Object::Ptr& obj)
return new Array(std::move(result));
}
+static Dictionary::Ptr GetTargetForTemplate(const ConfigItem::Ptr& item)
+{
+ DebugInfo di = item->GetDebugInfo();
+
+ return new Dictionary({
+ { "name", item->GetName() },
+ { "type", item->GetType()->GetName() },
+ { "location", new Dictionary({
+ { "path", di.Path },
+ { "first_line", di.FirstLine },
+ { "first_column", di.FirstColumn },
+ { "last_line", di.LastLine },
+ { "last_column", di.LastColumn }
+ }) }
+ });
+}
+
+Dictionary::Ptr ScriptUtils::GetTemplate(const Value& vtype, const String& name)
+{
+ Type::Ptr ptype;
+
+ if (vtype.IsObjectType())
+ ptype = vtype;
+ else
+ ptype = Type::GetByName(vtype);
+
+ ConfigItem::Ptr item = ConfigItem::GetByTypeAndName(ptype, name);
+
+ if (!item || !item->IsAbstract())
+ return nullptr;
+
+ DebugInfo di = item->GetDebugInfo();
+
+ return GetTargetForTemplate(item);
+}
+
+Array::Ptr ScriptUtils::GetTemplates(const Type::Ptr& type)
+{
+ if (!type)
+ BOOST_THROW_EXCEPTION(std::invalid_argument("Invalid type: Must not be null"));
+
+ ArrayData result;
+
+ for (const ConfigItem::Ptr& item : ConfigItem::GetItems(type)) {
+ if (item->IsAbstract())
+ result.push_back(GetTargetForTemplate(item));
+ }
+
+ return new Array(std::move(result));
+}
+
ConfigObject::Ptr ScriptUtils::GetObject(const Value& vtype, const String& name)
{
Type::Ptr ptype;
diff --git a/lib/base/scriptutils.hpp b/lib/base/scriptutils.hpp
index c874ff857..7bd3e8b9d 100644
--- a/lib/base/scriptutils.hpp
+++ b/lib/base/scriptutils.hpp
@@ -33,6 +33,8 @@ public:
static Array::Ptr Range(const std::vector& arguments);
static Type::Ptr TypeOf(const Value& value);
static Array::Ptr Keys(const Object::Ptr& obj);
+ static Dictionary::Ptr GetTemplate(const Value& vtype, const String& name);
+ static Array::Ptr GetTemplates(const Type::Ptr& type);
static ConfigObject::Ptr GetObject(const Value& type, const String& name);
static Array::Ptr GetObjects(const Type::Ptr& type);
static void Assert(const Value& arg);