Refactor commands and implement event handlers.

Fixes #3877
Fixes #4001
This commit is contained in:
Gunnar Beutner 2013-06-13 11:33:00 +02:00
parent 4fadd3bfa0
commit d042a181bd
33 changed files with 1091 additions and 273 deletions

View File

@ -79,7 +79,10 @@ void NotificationComponent::NotificationTimerHandler(void)
Service::Ptr service = notification->GetService(); Service::Ptr service = notification->GetService();
bool reachable = service->IsReachable(); bool reachable = service->IsReachable();
notification->SetNextNotification(Utility::GetTime() + notification->GetNotificationInterval()); {
ObjectLock olock(notification);
notification->SetNextNotification(Utility::GetTime() + notification->GetNotificationInterval());
}
bool send_notification; bool send_notification;

View File

@ -107,8 +107,8 @@ So far our Icinga 2 setup doesn't do much. Lets change that by setting up a serv
check for localhost. Modify your 'icinga2.conf' configuration file by adding the following lines: check for localhost. Modify your 'icinga2.conf' configuration file by adding the following lines:
---- ----
template Service "my-ping" inherits "plugin-service" { object CheckCommand "my-ping" inherits "plugin-check-command" {
check_command = [ command = [
"$plugindir$/check_ping", "$plugindir$/check_ping",
"-H", "$address$", "-H", "$address$",
"-w", "10,5%", "-w", "10,5%",
@ -116,6 +116,10 @@ template Service "my-ping" inherits "plugin-service" {
] ]
} }
template Service "my-ping" inherits "plugin-service" {
check_command = "my-ping"
}
object Host "localhost" { object Host "localhost" {
display_name = "Home, sweet home!", display_name = "Home, sweet home!",
@ -133,9 +137,9 @@ object Host "localhost" {
} }
---- ----
We're defining a service template called "my-ping" which inherits from the We're defining a command object called "my-ping" which inherits from the
'plugin-service' template. The 'plugin-service' template is provided as part of 'plugin-check-command' template. The 'plugin-check-command' template is provided as part of
the Icinga Template Library and describes how services are checked. the Icinga Template Library and describes how checks are performed.
In the case of plugin-based services this means that the command specified by In the case of plugin-based services this means that the command specified by
the 'check_command' property is executed. the 'check_command' property is executed.
@ -154,9 +158,12 @@ By convention the following macros are usually used:
|address6 |The IPv6 address of the host. |address6 |The IPv6 address of the host.
|=== |===
Note that the 'my-ping' template does not define a value for the 'address' macro. This Note that the 'my-ping' command object does not define a value for the 'address' macro. This
is perfectly fine as long as that macro is defined somewhere else (e.g. in the host). is perfectly fine as long as that macro is defined somewhere else (e.g. in the host).
We're also defining a service template called 'my-ping' which uses the command object
we just created.
Next we're defining a 'Host' object called 'localhost'. We're setting an optional Next we're defining a 'Host' object called 'localhost'. We're setting an optional
display_name which is used by the CGIs when showing that host in the host overview. display_name which is used by the CGIs when showing that host in the host overview.
@ -252,7 +259,7 @@ object Host "icinga.org" {
Restart your Icinga 2 instance and check the CGIs for your new service's state. Unless Restart your Icinga 2 instance and check the CGIs for your new service's state. Unless
you have a low-latency network connection you will note that the service's state is 'CRITICAL'. you have a low-latency network connection you will note that the service's state is 'CRITICAL'.
This is because in the 'my-ping' template we have hard-coded the timeout as 25 milliseconds. This is because in the 'my-ping' command object we have hard-coded the timeout as 25 milliseconds.
Ideally we'd be able to specify different timeouts for our new service. Using macros we Ideally we'd be able to specify different timeouts for our new service. Using macros we
can easily do this. can easily do this.
@ -260,11 +267,11 @@ can easily do this.
NOTE: If you've used Icinga 1.x before you're probably familiar with doing this by passing NOTE: If you've used Icinga 1.x before you're probably familiar with doing this by passing
ARGx macros to your check commands. ARGx macros to your check commands.
Start by replacing your 'my-ping' service template with this: Start by replacing your 'my-ping' command object with this:
---- ----
template Service "my-ping" inherits "plugin-service" { object CheckCommand "my-ping" inherits "plugin-check-command" {
check_command = [ command = [
"$plugindir$/check_ping", "$plugindir$/check_ping",
"-H", "$address$", "-H", "$address$",
"-w", "$wrta$,$wpl$%", "-w", "$wrta$,$wpl$%",
@ -329,12 +336,12 @@ NOTE: Ordinarily you'd use double-quotes for the include path. This way only pat
relative to the current configuration file are considered. The angle brackets tell relative to the current configuration file are considered. The angle brackets tell
Icinga 2 to search its list of global include directories. Icinga 2 to search its list of global include directories.
One of the templates in the ITL is the 'ping4' template which is quite similar One of the templates in the ITL is the 'ping4' service template which is quite similar
to our own 'my-ping' template: to our example objects:
---- ----
template Service "ping4" inherits "plugin-service" { object CheckCommand "ping4" inherits "plugin-check-command" {
check_command = [ command = [
"$plugindir$/check_ping", "$plugindir$/check_ping",
"-4", "-4",
"-H", "$address$", "-H", "$address$",
@ -355,6 +362,10 @@ template Service "ping4" inherits "plugin-service" {
timeout = 0 timeout = 0
} }
} }
template Service "ping4" {
check_command = "ping4"
}
---- ----
Lets simplify our configuration file by removing our custom 'my-ping' template and Lets simplify our configuration file by removing our custom 'my-ping' template and
@ -434,8 +445,8 @@ Next we're going to create a 'Notification' template which tells Icinga how to i
the shell script: the shell script:
---- ----
template Notification "mail-notification" inherits "plugin-notification" { object NotificationCommand "mail-notification" inherits "plugin-notification-command" {
notification_command = [ command = [
"/etc/icinga2/mail-notification.sh", "/etc/icinga2/mail-notification.sh",
"$email$" "$email$"
], ],
@ -451,6 +462,10 @@ template Notification "mail-notification" inherits "plugin-notification" {
"SERVICEOUTPUT" "SERVICEOUTPUT"
] ]
} }
template Notification "mail-notification" inherits "plugin-notification" {
notification_command = "mail-notification"
}
---- ----
NOTE: Rather than adding these templates to your main configuration file you might want NOTE: Rather than adding these templates to your main configuration file you might want

View File

@ -1,6 +1,8 @@
icinga2itldir = ${pkgdatadir}/itl icinga2itldir = ${pkgdatadir}/itl
icinga2itl_DATA = \ icinga2itl_DATA = \
cluster.conf \ cluster.conf \
command.conf \
command-common.conf \
itl.conf \ itl.conf \
host.conf \ host.conf \
notification.conf \ notification.conf \

224
itl/command-common.conf Normal file
View File

@ -0,0 +1,224 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
object CheckCommand "ping4" inherits "plugin-check-command" {
command = [
"$plugindir$/check_ping",
"-4",
"-H", "$address$",
"-w", "$wrta$,$wpl$%",
"-c", "$crta$,$cpl$%",
"-p", "$packets$",
"-t", "$timeout$"
],
macros = {
wrta = 100,
wpl = 5,
crta = 200,
cpl = 15,
packets = 5,
timeout = 0
}
}
object CheckCommand "ping6" inherits "plugin-check-command" {
command = [
"$plugindir$/check_ping",
"-6",
"-H", "$address6$",
"-w", "$wrta$,$wpl$%",
"-c", "$crta$,$cpl$%",
"-p", "$packets$",
"-t", "$timeout$"
],
macros = {
wrta = 100,
wpl = 5,
crta = 200,
cpl = 15,
packets = 5,
timeout = 0
}
}
object CheckCommand "dummy" inherits "plugin-check-command" {
command = [
"$plugindir$/check_dummy",
"$state$",
"$text$"
],
macros = {
state = 0,
text = "Check was successful."
}
}
object CheckCommand "tcp" inherits "plugin-check-command" {
command = [
"$plugindir$/check_tcp",
"-H", "$address$",
"-p", "$port$"
]
}
object CheckCommand "udp" inherits "plugin-check-command" {
command = [
"$plugindir$/check_udp",
"-H", "$address$",
"-p", "$port$"
]
}
object CheckCommand "http_vhost" inherits "plugin-check-command" {
command = [
"$plugindir$/check_http",
"-H", "$vhost$"
]
}
object CheckCommand "http_ip" inherits "plugin-check-command" {
command = [
"$plugindir$/check_ip",
"-H", "$address$"
]
}
object CheckCommand "https_vhost" inherits "plugin-check-command" {
command = [
"$plugindir$/check_http",
"-H", "$vhost", "-S"
]
}
object CheckCommand "https_ip" inherits "plugin-check-command" {
command = [
"$plugindir$/check_http",
"-I", "$address$", "-S"
]
}
object CheckCommand "smtp" inherits "plugin-check-command" {
command = [
"$plugindir$/check_smtp",
"-H", "$address$"
]
}
object CheckCommand "ssmtp" inherits "plugin-check-command" {
command = [
"$plugindir$/check_ssmtp",
"-H", "$address$",
"-p", "$port$"
],
macros += {
port = 465
}
}
object CheckCommand "ntp_time" inherits "plugin-check-command" {
command = [
"$plugindir$/check_ntp_time",
"-H", "$address$"
]
}
object CheckCommand "ssh" inherits "plugin-check-command" {
command = [
"$plugindir$/check_ssh",
"$address$"
]
}
object CheckCommand "disk" inherits "plugin-check-command" {
command = [
"$plugindir$/check_disk",
"-w", "$wfree$",
"-c", "$cfree$"
],
macros += {
wfree = "20%",
cfree = "10%",
}
}
object CheckCommand "users" inherits "plugin-check-command" {
command = [
"$plugindir$/check_users",
"-w", "$wgreater$",
"-c", "$cgreater$"
],
macros += {
wgreater = 20,
cgreater = 50,
}
}
object CheckCommand "processes" inherits "plugin-check-command" {
command = [
"$plugindir$/check_procs",
"-w", "$wgreater$",
"-c", "$cgreater$"
],
macros += {
wgreater = 250,
cgreater = 400,
}
}
object CheckCommand "load" inherits "plugin-check-command" {
command = [
"$plugindir$/check_load",
"-w", "$wload1$,$wload5$,$wload15$",
"-c", "$cload1$,$cload5$,$cload15$"
],
macros = {
wload1 = 5.0,
wload5 = 4.0,
wload15 = 3.0,
cload1 = 10.0,
cload5 = 6.0,
cload15 = 4.0
}
}
object CheckCommand "snmp" inherits "plugin-check-command" {
command = [
"$plugindir$/check_snmp",
"-H", "$address$",
"-o", "$oid$",
"-C", "$community$"
],
macros = {
community = "public"
}
}

36
itl/command.conf Normal file
View File

@ -0,0 +1,36 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
template CheckCommand "plugin-check-command" {
methods = {
execute = "PluginCheck"
}
}
template NotificationCommand "plugin-notification-command" {
methods = {
execute = "PluginNotification"
}
}
template EventCommand "plugin-event-command" {
methods = {
execute = "PluginEvent"
}
}

View File

@ -23,6 +23,8 @@
*/ */
include "host.conf" include "host.conf"
include "command.conf"
include "command-common.conf"
include "service.conf" include "service.conf"
include "service-common.conf" include "service-common.conf"
include "notification.conf" include "notification.conf"

View File

@ -17,211 +17,76 @@
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. * * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/ ******************************************************************************/
template Service "ping4" inherits "plugin-service" { template Service "ping4" {
check_command = [ check_command = "ping4"
"$plugindir$/check_ping",
"-4",
"-H", "$address$",
"-w", "$wrta$,$wpl$%",
"-c", "$crta$,$cpl$%",
"-p", "$packets$",
"-t", "$timeout$"
],
macros = {
wrta = 100,
wpl = 5,
crta = 200,
cpl = 15,
packets = 5,
timeout = 0
}
} }
template Service "ping6" inherits "plugin-service" { template Service "ping6" {
check_command = [ check_command = "ping6"
"$plugindir$/check_ping",
"-6",
"-H", "$address6$",
"-w", "$wrta$,$wpl$%",
"-c", "$crta$,$cpl$%",
"-p", "$packets$",
"-t", "$timeout$"
],
macros = {
wrta = 100,
wpl = 5,
crta = 200,
cpl = 15,
packets = 5,
timeout = 0
}
} }
template Service "dummy" inherits "plugin-service" { template Service "dummy" {
check_command = [ check_command = "dummy"
"$plugindir$/check_dummy",
"$state$",
"$text$"
],
macros = {
state = 0,
text = "Check was successful."
}
} }
template Service "tcp" inherits "plugin-service" { template Service "tcp" {
check_command = [ check_command = "tcp"
"$plugindir$/check_tcp",
"-H", "$address$",
"-p", "$port$"
]
} }
template Service "udp" inherits "plugin-service" { template Service "udp" {
check_command = [ check_command = "udp"
"$plugindir$/check_udp",
"-H", "$address$",
"-p", "$port$"
]
} }
template Service "http_vhost" inherits "plugin-service" { template Service "http_vhost" {
check_command = [ check_command = "http_vhost"
"$plugindir$/check_http",
"-H", "$vhost$"
],
} }
template Service "http_ip" inherits "plugin-service" { template Service "http_ip" {
check_command = [ check_command = "http_ip"
"$plugindir$/check_http",
"-I", "$address$"
]
} }
template Service "https_vhost" inherits "plugin-service" { template Service "https_vhost" {
check_command = [ check_command = "https_vhost"
"$plugindir$/check_http",
"-H", "$vhost", "-S"
],
} }
template Service "https_ip" inherits "plugin-service" { template Service "https_ip" {
check_command = [ check_command = "https_ip"
"$plugindir$/check_http",
"-I", "$address$", "-S"
],
} }
template Service "smtp" inherits "plugin-service" { template Service "smtp" {
check_command = [ check_command = "smtp"
"$plugindir$/check_smtp",
"-H", "$address$"
]
} }
template Service "ssmtp" inherits "plugin-service" { template Service "ssmtp" {
check_command = [ check_command = "ssmtp"
"$plugindir$/check_ssmtp",
"-H", "$address$",
"-p", "$port$"
],
macros += {
port = 465
}
} }
template Service "ntp_time" inherits "plugin-service" { template Service "ntp_time" {
check_command = [ check_command = "ntp_time"
"$plugindir$/check_ntp_time",
"-H", "$address$"
]
} }
template Service "ssh" inherits "plugin-service" { template Service "ssh" {
check_command = [ check_command = "ssh"
"$plugindir$/check_ssh",
"$address$"
]
} }
template Service "disk" inherits "plugin-service" { template Service "disk" {
check_command = [ check_command = "disk"
"$plugindir$/check_disk",
"-w", "$wfree$",
"-c", "$cfree$"
],
macros += {
wfree = "20%",
cfree = "10%",
}
} }
template Service "users" inherits "plugin-service" { template Service "users" {
check_command = [ check_command = "users"
"$plugindir$/check_users",
"-w", "$wgreater$",
"-c", "$cgreater$"
],
macros += {
wgreater = 20,
cgreater = 50,
}
} }
template Service "processes" inherits "plugin-service" { template Service "processes" {
check_command = [ check_command = "processes"
"$plugindir$/check_procs",
"-w", "$wgreater$",
"-c", "$cgreater$"
],
macros += {
wgreater = 250,
cgreater = 400,
}
} }
template Service "load" {
template Service "load" inherits "plugin-service" { check_command = "load"
check_command = [
"$plugindir$/check_load",
"-w", "$wload1$,$wload5$,$wload15$",
"-c", "$cload1$,$cload5$,$cload15$"
],
macros = {
wload1 = 5.0,
wload5 = 4.0,
wload15 = 3.0,
cload1 = 10.0,
cload5 = 6.0,
cload15 = 4.0
}
} }
template Service "snmp" inherits "plugin-service" { template Service "snmp" {
check_command = [ check_command = "snmp"
"$plugindir$/check_snmp",
"-H", "$address$",
"-o", "$oid$",
"-C", "$community$"
],
macros = {
community = "public"
}
} }
template Service "snmp-uptime" inherits "snmp" { template Service "snmp-uptime" inherits "snmp" {

View File

@ -18,6 +18,7 @@
******************************************************************************/ ******************************************************************************/
#include "base/object.h" #include "base/object.h"
#include "base/value.h"
using namespace icinga; using namespace icinga;
@ -63,3 +64,8 @@ bool Object::OwnsLock(void) const
return (m_Locked && m_LockOwner == boost::this_thread::get_id()); return (m_Locked && m_LockOwner == boost::this_thread::get_id());
} }
#endif /* _DEBUG */ #endif /* _DEBUG */
Object::SharedPtrHolder::operator Value(void) const
{
return m_Object;
}

View File

@ -42,7 +42,7 @@ using boost::static_pointer_cast;
namespace icinga namespace icinga
{ {
class SharedPtrHolder; class Value;
/** /**
* Base class for all heap-allocated objects. At least one of its methods * Base class for all heap-allocated objects. At least one of its methods
@ -108,6 +108,8 @@ public:
return static_cast<shared_ptr<T> >(*this); return static_cast<shared_ptr<T> >(*this);
} }
operator Value(void) const;
private: private:
Object::Ptr m_Object; /**< The object that belongs to this Object::Ptr m_Object; /**< The object that belongs to this
holder instance */ holder instance */

View File

@ -13,10 +13,16 @@ EXTRA_DIST = \
libicinga_la_SOURCES = \ libicinga_la_SOURCES = \
api.cpp \ api.cpp \
api.h \ api.h \
checkcommand.cpp \
checkcommand.h \
checkresultmessage.cpp \ checkresultmessage.cpp \
checkresultmessage.h \ checkresultmessage.h \
cib.cpp \ cib.cpp \
cib.h \ cib.h \
command.cpp \
command.h \
eventcommand.cpp \
eventcommand.h \
externalcommandprocessor.cpp \ externalcommandprocessor.cpp \
externalcommandprocessor.h \ externalcommandprocessor.h \
host.cpp \ host.cpp \
@ -35,20 +41,27 @@ libicinga_la_SOURCES = \
macroresolver.h \ macroresolver.h \
notification.cpp \ notification.cpp \
notification.h \ notification.h \
notificationcommand.cpp \
notificationcommand.h \
notificationrequestmessage.cpp \ notificationrequestmessage.cpp \
notificationrequestmessage.h \ notificationrequestmessage.h \
nullchecktask.cpp \ nullchecktask.cpp \
nullchecktask.h \ nullchecktask.h \
nulleventtask.cpp \
nulleventtask.h \
perfdatawriter.cpp \ perfdatawriter.cpp \
perfdatawriter.h \ perfdatawriter.h \
pluginchecktask.cpp \ pluginchecktask.cpp \
pluginchecktask.h \ pluginchecktask.h \
plugineventtask.cpp \
plugineventtask.h \
pluginnotificationtask.cpp \ pluginnotificationtask.cpp \
pluginnotificationtask.h \ pluginnotificationtask.h \
service.cpp \ service.cpp \
service-check.cpp \ service-check.cpp \
service-comment.cpp \ service-comment.cpp \
service-downtime.cpp \ service-downtime.cpp \
service-event.cpp \
service-notification.cpp \ service-notification.cpp \
service.h \ service.h \
servicegroup.cpp \ servicegroup.cpp \

View File

@ -0,0 +1,48 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#include "icinga/checkcommand.h"
#include "base/dynamictype.h"
using namespace icinga;
REGISTER_TYPE(CheckCommand);
/**
* Constructor for the CheckCommand class.
*
* @param serializedUpdate A serialized dictionary containing attributes.
*/
CheckCommand::CheckCommand(const Dictionary::Ptr& serializedUpdate)
: Command(serializedUpdate)
{ }
CheckCommand::Ptr CheckCommand::GetByName(const String& name)
{
DynamicObject::Ptr configObject = DynamicObject::GetObject("CheckCommand", name);
return dynamic_pointer_cast<CheckCommand>(configObject);
}
Dictionary::Ptr CheckCommand::Execute(const Service::Ptr& service)
{
std::vector<Value> arguments;
arguments.push_back(service);
return InvokeMethod("execute", arguments);
}

49
lib/icinga/checkcommand.h Normal file
View File

@ -0,0 +1,49 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#ifndef CHECKCOMMAND_H
#define CHECKCOMMAND_H
#include "icinga/command.h"
#include "icinga/service.h"
namespace icinga
{
/**
* A command.
*
* @ingroup base
*/
class I2_BASE_API CheckCommand : public Command
{
public:
typedef shared_ptr<CheckCommand> Ptr;
typedef weak_ptr<CheckCommand> WeakPtr;
explicit CheckCommand(const Dictionary::Ptr& serializedUpdate);
static CheckCommand::Ptr GetByName(const String& name);
virtual Dictionary::Ptr Execute(const Service::Ptr& service);
};
}
#endif /* CHECKCOMMAND_H */

56
lib/icinga/command.cpp Normal file
View File

@ -0,0 +1,56 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#include "icinga/command.h"
using namespace icinga;
/**
* Constructor for the Command class.
*
* @param serializedUpdate A serialized dictionary containing attributes.
*/
Command::Command(const Dictionary::Ptr& serializedUpdate)
: DynamicObject(serializedUpdate)
{
RegisterAttribute("macros", Attribute_Config, &m_Macros);
RegisterAttribute("export_macros", Attribute_Config, &m_ExportMacros);
}
Dictionary::Ptr Command::GetMacros(void) const
{
return m_Macros;
}
Array::Ptr Command::GetExportMacros(void) const
{
return m_ExportMacros;
}
bool Command::ResolveMacro(const String& macro, const Dictionary::Ptr& cr, String *result) const
{
Dictionary::Ptr macros = GetMacros();
if (macros && macros->Contains(macro)) {
*result = macros->Get(macro);
return true;
}
return false;
}

59
lib/icinga/command.h Normal file
View File

@ -0,0 +1,59 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#ifndef COMMAND_H
#define COMMAND_H
#include "icinga/macroresolver.h"
#include "base/i2-base.h"
#include "base/array.h"
#include "base/dynamicobject.h"
#include "base/logger_fwd.h"
#include <set>
namespace icinga
{
/**
* A command.
*
* @ingroup base
*/
class I2_BASE_API Command : public DynamicObject, public MacroResolver
{
public:
typedef shared_ptr<Command> Ptr;
typedef weak_ptr<Command> WeakPtr;
explicit Command(const Dictionary::Ptr& serializedUpdate);
//virtual Dictionary::Ptr Execute(const Object::Ptr& context) = 0;
Dictionary::Ptr GetMacros(void) const;
Array::Ptr GetExportMacros(void) const;
virtual bool ResolveMacro(const String& macro, const Dictionary::Ptr& cr, String *result) const;
private:
Attribute<Dictionary::Ptr> m_Macros;
Attribute<Array::Ptr> m_ExportMacros;
};
}
#endif /* COMMAND_H */

View File

@ -0,0 +1,48 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#include "icinga/eventcommand.h"
#include "base/dynamictype.h"
using namespace icinga;
REGISTER_TYPE(EventCommand);
/**
* Constructor for the EventCommand class.
*
* @param serializedUpdate A serialized dictionary containing attributes.
*/
EventCommand::EventCommand(const Dictionary::Ptr& serializedUpdate)
: Command(serializedUpdate)
{ }
EventCommand::Ptr EventCommand::GetByName(const String& name)
{
DynamicObject::Ptr configObject = DynamicObject::GetObject("EventCommand", name);
return dynamic_pointer_cast<EventCommand>(configObject);
}
void EventCommand::Execute(const Service::Ptr& service)
{
std::vector<Value> arguments;
arguments.push_back(service);
InvokeMethod("execute", arguments);
}

49
lib/icinga/eventcommand.h Normal file
View File

@ -0,0 +1,49 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#ifndef EVENTCOMMAND_H
#define EVENTCOMMAND_H
#include "icinga/command.h"
#include "icinga/service.h"
namespace icinga
{
/**
* An event handler command.
*
* @ingroup base
*/
class I2_BASE_API EventCommand : public Command
{
public:
typedef shared_ptr<EventCommand> Ptr;
typedef weak_ptr<EventCommand> WeakPtr;
explicit EventCommand(const Dictionary::Ptr& serializedUpdate);
static EventCommand::Ptr GetByName(const String& name);
virtual void Execute(const Service::Ptr& context);
};
}
#endif /* EVENTCOMMAND_H */

View File

@ -50,8 +50,6 @@ type Host {
%attribute string "*" %attribute string "*"
}, },
%attribute array "export_macros",
%attribute name(TimePeriod) "check_period", %attribute name(TimePeriod) "check_period",
%attribute number "check_interval", %attribute number "check_interval",
%attribute number "retry_interval", %attribute number "retry_interval",
@ -88,10 +86,6 @@ type Host {
%attribute string "*" %attribute string "*"
}, },
%attribute array "export_macros" {
%attribute string "*"
},
%attribute array "users" { %attribute array "users" {
%attribute name(User) "*" %attribute name(User) "*"
}, },
@ -118,10 +112,6 @@ type Host {
%attribute string "*" %attribute string "*"
}, },
%attribute array "export_macros" {
%attribute string "*"
},
%attribute array "users" { %attribute array "users" {
%attribute name(User) "*" %attribute name(User) "*"
}, },
@ -149,10 +139,6 @@ type Host {
%attribute string "*" %attribute string "*"
}, },
%attribute array "export_macros" {
%attribute string "*"
},
%attribute array "servicegroups" { %attribute array "servicegroups" {
%attribute name(ServiceGroup) "*" %attribute name(ServiceGroup) "*"
}, },
@ -190,19 +176,15 @@ type Service {
%attribute string "*" %attribute string "*"
}, },
%attribute array "export_macros" { %require "check_command",
%attribute string "*" %attribute name(CheckCommand) "check_command",
},
%attribute array "check_command" {
%attribute string "*"
},
%attribute string "check_command",
%attribute number "max_check_attempts", %attribute number "max_check_attempts",
%attribute name(TimePeriod) "check_period", %attribute name(TimePeriod) "check_period",
%attribute number "check_interval", %attribute number "check_interval",
%attribute number "retry_interval", %attribute number "retry_interval",
%attribute name(EventCommand) "event_command",
%attribute number "notification_interval", %attribute number "notification_interval",
%attribute name(TimePeriod) "notification_period", %attribute name(TimePeriod) "notification_period",
@ -225,12 +207,6 @@ type Service {
%attribute string "*" %attribute string "*"
}, },
%require "methods",
%attribute dictionary "methods" {
%require "check",
%attribute string "check"
},
%attribute dictionary "notifications" { %attribute dictionary "notifications" {
%attribute dictionary "*" { %attribute dictionary "*" {
%attribute array "templates" { %attribute array "templates" {
@ -241,10 +217,6 @@ type Service {
%attribute string "*" %attribute string "*"
}, },
%attribute array "export_macros" {
%attribute string "*"
},
%attribute array "users" { %attribute array "users" {
%attribute name(User) "*" %attribute name(User) "*"
}, },
@ -268,12 +240,6 @@ type ServiceGroup {
} }
type Notification { type Notification {
%require "methods",
%attribute dictionary "methods" {
%require "notify",
%attribute string "notify"
},
%require "host_name", %require "host_name",
%attribute string "host_name", %attribute string "host_name",
%attribute string "service", %attribute string "service",
@ -282,10 +248,6 @@ type Notification {
%attribute string "*" %attribute string "*"
}, },
%attribute array "export_macros" {
%attribute string "*"
},
%attribute array "users" { %attribute array "users" {
%attribute name(User) "*" %attribute name(User) "*"
}, },
@ -298,10 +260,7 @@ type Notification {
%attribute number "end", %attribute number "end",
}, },
%attribute array "notification_command" { %attribute name(NotificationCommand) "notification_command",
%attribute string "*"
},
%attribute string "notification_command",
%attribute number "notification_interval", %attribute number "notification_interval",
%attribute name(TimePeriod) "notification_period" %attribute name(TimePeriod) "notification_period"
@ -338,3 +297,37 @@ type PerfdataWriter {
%attribute string "format_template", %attribute string "format_template",
%attribute number "rotation_interval" %attribute number "rotation_interval"
} }
type Command {
%require "methods",
%attribute dictionary "methods" {
%require "execute",
%attribute string "execute"
},
/* %if (methods.execute == "PluginNotification" || methods.execute == "PluginCheck" || methods.execute == "PluginEvent") { */
// %require "command",
%attribute string "command",
%attribute array "command" {
%attribute string "*"
},
%attribute array "export_macros" {
%attribute string "*"
},
%attribute dictionary "macros" {
%attribute string "*"
}
/* } */
}
type CheckCommand inherits Command {
}
type NotificationCommand inherits Command {
}
type EventCommand inherits Command {
}

View File

@ -384,8 +384,6 @@ Array::Ptr LegacyTimePeriod::ScriptFunc(const TimePeriod::Ptr& tp, double begin,
Dictionary::Ptr ranges = tp->Get("ranges"); Dictionary::Ptr ranges = tp->Get("ranges");
if (ranges) { if (ranges) {
for (int i = 0; i <= (end - begin) / (24 * 60 * 60); i++) { for (int i = 0; i <= (end - begin) / (24 * 60 * 60); i++) {
time_t refts = begin + i * 24 * 60 * 60; time_t refts = begin + i * 24 * 60 * 60;

View File

@ -18,6 +18,7 @@
******************************************************************************/ ******************************************************************************/
#include "icinga/notification.h" #include "icinga/notification.h"
#include "icinga/notificationcommand.h"
#include "icinga/macroprocessor.h" #include "icinga/macroprocessor.h"
#include "icinga/service.h" #include "icinga/service.h"
#include "base/dynamictype.h" #include "base/dynamictype.h"
@ -74,9 +75,9 @@ Service::Ptr Notification::GetService(void) const
return host->GetServiceByShortName(m_Service); return host->GetServiceByShortName(m_Service);
} }
Value Notification::GetNotificationCommand(void) const NotificationCommand::Ptr Notification::GetNotificationCommand(void) const
{ {
return m_NotificationCommand; return NotificationCommand::GetByName(m_NotificationCommand);
} }
Dictionary::Ptr Notification::GetMacros(void) const Dictionary::Ptr Notification::GetMacros(void) const
@ -252,7 +253,7 @@ void Notification::BeginExecuteNotification(NotificationType type, const Diction
} }
BOOST_FOREACH(const User::Ptr& user, allUsers) { BOOST_FOREACH(const User::Ptr& user, allUsers) {
Log(LogDebug, "icinga", "Sending notification for user " + user->GetName()); Log(LogDebug, "icinga", "Sending notification for user '" + user->GetName() + "'");
Utility::QueueAsyncCallback(boost::bind(&Notification::ExecuteNotificationHelper, this, type, user, cr, force)); Utility::QueueAsyncCallback(boost::bind(&Notification::ExecuteNotificationHelper, this, type, user, cr, force));
} }
} }
@ -271,16 +272,8 @@ void Notification::ExecuteNotificationHelper(NotificationType type, const User::
} }
} }
Notification::Ptr self = GetSelf();
std::vector<Value> arguments;
arguments.push_back(self);
arguments.push_back(user);
arguments.push_back(cr);
arguments.push_back(type);
try { try {
InvokeMethod("notify", arguments); GetNotificationCommand()->Execute(GetSelf(), user, cr, type);
Log(LogInformation, "icinga", "Completed sending notification for service '" + GetService()->GetName() + "'"); Log(LogInformation, "icinga", "Completed sending notification for service '" + GetService()->GetName() + "'");
} catch (const std::exception& ex) { } catch (const std::exception& ex) {

View File

@ -46,6 +46,7 @@ enum NotificationType
}; };
class Service; class Service;
class NotificationCommand;
/** /**
* An Icinga notification specification. * An Icinga notification specification.
@ -64,7 +65,7 @@ public:
static Notification::Ptr GetByName(const String& name); static Notification::Ptr GetByName(const String& name);
shared_ptr<Service> GetService(void) const; shared_ptr<Service> GetService(void) const;
Value GetNotificationCommand(void) const; shared_ptr<NotificationCommand> GetNotificationCommand(void) const;
double GetNotificationInterval(void) const; double GetNotificationInterval(void) const;
TimePeriod::Ptr GetNotificationPeriod(void) const; TimePeriod::Ptr GetNotificationPeriod(void) const;
Dictionary::Ptr GetMacros(void) const; Dictionary::Ptr GetMacros(void) const;
@ -89,7 +90,7 @@ protected:
void OnAttributeChanged(const String& name); void OnAttributeChanged(const String& name);
private: private:
Attribute<Value> m_NotificationCommand; Attribute<String> m_NotificationCommand;
Attribute<double> m_NotificationInterval; Attribute<double> m_NotificationInterval;
Attribute<String> m_NotificationPeriod; Attribute<String> m_NotificationPeriod;
Attribute<double> m_LastNotification; Attribute<double> m_LastNotification;

View File

@ -0,0 +1,52 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#include "icinga/notificationcommand.h"
#include "base/dynamictype.h"
using namespace icinga;
REGISTER_TYPE(NotificationCommand);
/**
* Constructor for the NotificationCommand class.
*
* @param serializedUpdate A serialized dictionary containing attributes.
*/
NotificationCommand::NotificationCommand(const Dictionary::Ptr& serializedUpdate)
: Command(serializedUpdate)
{ }
NotificationCommand::Ptr NotificationCommand::GetByName(const String& name)
{
DynamicObject::Ptr configObject = DynamicObject::GetObject("NotificationCommand", name);
return dynamic_pointer_cast<NotificationCommand>(configObject);
}
Dictionary::Ptr NotificationCommand::Execute(const Notification::Ptr& notification,
const User::Ptr& user, const Dictionary::Ptr& cr, const NotificationType& type)
{
std::vector<Value> arguments;
arguments.push_back(notification);
arguments.push_back(user);
arguments.push_back(cr);
arguments.push_back(type);
return InvokeMethod("execute", arguments);
}

View File

@ -0,0 +1,52 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#ifndef NOTIFICATIONCOMMAND_H
#define NOTIFICATIONCOMMAND_H
#include "icinga/command.h"
#include "icinga/notification.h"
namespace icinga
{
class Notification;
/**
* A notification command.
*
* @ingroup base
*/
class I2_BASE_API NotificationCommand : public Command
{
public:
typedef shared_ptr<NotificationCommand> Ptr;
typedef weak_ptr<NotificationCommand> WeakPtr;
explicit NotificationCommand(const Dictionary::Ptr& serializedUpdate);
static NotificationCommand::Ptr GetByName(const String& name);
virtual Dictionary::Ptr Execute(const shared_ptr<Notification>& notification,
const User::Ptr& user, const Dictionary::Ptr& cr, const NotificationType& type);
};
}
#endif /* NOTIFICATIONCOMMAND_H */

View File

@ -19,13 +19,14 @@
#include "icinga/nullchecktask.h" #include "icinga/nullchecktask.h"
#include "base/scriptfunction.h" #include "base/scriptfunction.h"
#include "base/logger_fwd.h"
#include <boost/smart_ptr/make_shared.hpp> #include <boost/smart_ptr/make_shared.hpp>
using namespace icinga; using namespace icinga;
REGISTER_SCRIPTFUNCTION(NullCheck, &NullCheckTask::ScriptFunc); REGISTER_SCRIPTFUNCTION(NullCheck, &NullCheckTask::ScriptFunc);
Dictionary::Ptr NullCheckTask::ScriptFunc(const Service::Ptr&) Dictionary::Ptr NullCheckTask::ScriptFunc(const Service::Ptr& service)
{ {
Dictionary::Ptr cr = boost::make_shared<Dictionary>(); Dictionary::Ptr cr = boost::make_shared<Dictionary>();
cr->Set("state", StateUnknown); cr->Set("state", StateUnknown);

View File

@ -0,0 +1,31 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#include "icinga/nulleventtask.h"
#include "base/scriptfunction.h"
#include "base/logger_fwd.h"
#include <boost/smart_ptr/make_shared.hpp>
using namespace icinga;
REGISTER_SCRIPTFUNCTION(NullEvent, &NullEventTask::ScriptFunc);
void NullEventTask::ScriptFunc(const Service::Ptr& service)
{
}

View File

@ -0,0 +1,46 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#ifndef NULLEVENTTASK_H
#define NULLEVENTTASK_H
#include "icinga/i2-icinga.h"
#include "icinga/service.h"
#include "base/dictionary.h"
namespace icinga
{
/**
* Test class for additional event handler types. Implements the "null" event handler type.
*
* @ingroup icinga
*/
class I2_ICINGA_API NullEventTask
{
public:
static void ScriptFunc(const Service::Ptr& service);
private:
NullEventTask(void);
};
}
#endif /* NULLEVENTTASK_H */

View File

@ -18,6 +18,7 @@
******************************************************************************/ ******************************************************************************/
#include "icinga/pluginchecktask.h" #include "icinga/pluginchecktask.h"
#include "icinga/checkcommand.h"
#include "icinga/macroprocessor.h" #include "icinga/macroprocessor.h"
#include "icinga/icingaapplication.h" #include "icinga/icingaapplication.h"
#include "base/dynamictype.h" #include "base/dynamictype.h"
@ -36,9 +37,11 @@ REGISTER_SCRIPTFUNCTION(PluginCheck, &PluginCheckTask::ScriptFunc);
Dictionary::Ptr PluginCheckTask::ScriptFunc(const Service::Ptr& service) Dictionary::Ptr PluginCheckTask::ScriptFunc(const Service::Ptr& service)
{ {
Value raw_command = service->GetCheckCommand(); CheckCommand::Ptr commandObj = service->GetCheckCommand();
Value raw_command = commandObj->Get("command");
std::vector<MacroResolver::Ptr> resolvers; std::vector<MacroResolver::Ptr> resolvers;
resolvers.push_back(commandObj);
resolvers.push_back(service); resolvers.push_back(service);
resolvers.push_back(service->GetHost()); resolvers.push_back(service->GetHost());
resolvers.push_back(IcingaApplication::GetInstance()); resolvers.push_back(IcingaApplication::GetInstance());
@ -47,7 +50,7 @@ Dictionary::Ptr PluginCheckTask::ScriptFunc(const Service::Ptr& service)
Dictionary::Ptr envMacros = boost::make_shared<Dictionary>(); Dictionary::Ptr envMacros = boost::make_shared<Dictionary>();
Array::Ptr export_macros = service->GetExportMacros(); Array::Ptr export_macros = commandObj->GetExportMacros();
if (export_macros) { if (export_macros) {
BOOST_FOREACH(const String& macro, export_macros) { BOOST_FOREACH(const String& macro, export_macros) {

View File

@ -0,0 +1,69 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#include "icinga/plugineventtask.h"
#include "icinga/eventcommand.h"
#include "icinga/macroprocessor.h"
#include "icinga/icingaapplication.h"
#include "base/dynamictype.h"
#include "base/logger_fwd.h"
#include "base/scriptfunction.h"
#include "base/utility.h"
#include "base/process.h"
#include <boost/smart_ptr/make_shared.hpp>
#include <boost/foreach.hpp>
using namespace icinga;
REGISTER_SCRIPTFUNCTION(PluginEvent, &PluginEventTask::ScriptFunc);
void PluginEventTask::ScriptFunc(const Service::Ptr& service)
{
EventCommand::Ptr commandObj = service->GetEventCommand();
Value raw_command = commandObj->Get("command");
std::vector<MacroResolver::Ptr> resolvers;
resolvers.push_back(commandObj);
resolvers.push_back(service);
resolvers.push_back(service->GetHost());
resolvers.push_back(IcingaApplication::GetInstance());
Value command = MacroProcessor::ResolveMacros(raw_command, resolvers, Dictionary::Ptr(), Utility::EscapeShellCmd);
Dictionary::Ptr envMacros = boost::make_shared<Dictionary>();
Array::Ptr export_macros = commandObj->GetExportMacros();
if (export_macros) {
BOOST_FOREACH(const String& macro, export_macros) {
String value;
if (!MacroProcessor::ResolveMacro(macro, resolvers, Dictionary::Ptr(), &value)) {
Log(LogWarning, "icinga", "export_macros for command '" + commandObj->GetName() + "' refers to unknown macro '" + macro + "'");
continue;
}
envMacros->Set(macro, value);
}
}
Process::Ptr process = boost::make_shared<Process>(Process::SplitCommand(command), envMacros);
process->Run();
}

View File

@ -0,0 +1,45 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#ifndef PLUGINEVENTTASK_H
#define PLUGINEVENTTASK_H
#include "icinga/i2-icinga.h"
#include "icinga/service.h"
namespace icinga
{
/**
* Implements event handlers based on external plugins.
*
* @ingroup icinga
*/
class I2_ICINGA_API PluginEventTask
{
public:
static void ScriptFunc(const Service::Ptr& service);
private:
PluginEventTask(void);
};
}
#endif /* PLUGINEVENTTASK_H */

View File

@ -19,6 +19,7 @@
#include "icinga/pluginnotificationtask.h" #include "icinga/pluginnotificationtask.h"
#include "icinga/notification.h" #include "icinga/notification.h"
#include "icinga/notificationcommand.h"
#include "icinga/service.h" #include "icinga/service.h"
#include "icinga/macroprocessor.h" #include "icinga/macroprocessor.h"
#include "icinga/icingaapplication.h" #include "icinga/icingaapplication.h"
@ -36,11 +37,13 @@ REGISTER_SCRIPTFUNCTION(PluginNotification, &PluginNotificationTask::ScriptFunc)
void PluginNotificationTask::ScriptFunc(const Notification::Ptr& notification, const User::Ptr& user, const Dictionary::Ptr& cr, int itype) void PluginNotificationTask::ScriptFunc(const Notification::Ptr& notification, const User::Ptr& user, const Dictionary::Ptr& cr, int itype)
{ {
NotificationCommand::Ptr commandObj = notification->GetNotificationCommand();
NotificationType type = static_cast<NotificationType>(itype); NotificationType type = static_cast<NotificationType>(itype);
Service::Ptr service = notification->GetService(); Service::Ptr service = notification->GetService();
Value raw_command = notification->GetNotificationCommand(); Value raw_command = commandObj->Get("command");
StaticMacroResolver::Ptr notificationMacroResolver = boost::make_shared<StaticMacroResolver>(); StaticMacroResolver::Ptr notificationMacroResolver = boost::make_shared<StaticMacroResolver>();
notificationMacroResolver->Add("NOTIFICATIONTYPE", Notification::NotificationTypeToString(type)); notificationMacroResolver->Add("NOTIFICATIONTYPE", Notification::NotificationTypeToString(type));
@ -48,6 +51,7 @@ void PluginNotificationTask::ScriptFunc(const Notification::Ptr& notification, c
std::vector<MacroResolver::Ptr> resolvers; std::vector<MacroResolver::Ptr> resolvers;
resolvers.push_back(user); resolvers.push_back(user);
resolvers.push_back(notificationMacroResolver); resolvers.push_back(notificationMacroResolver);
resolvers.push_back(commandObj);
resolvers.push_back(notification); resolvers.push_back(notification);
resolvers.push_back(service); resolvers.push_back(service);
resolvers.push_back(service->GetHost()); resolvers.push_back(service->GetHost());

View File

@ -18,6 +18,7 @@
******************************************************************************/ ******************************************************************************/
#include "icinga/service.h" #include "icinga/service.h"
#include "icinga/checkcommand.h"
#include "icinga/icingaapplication.h" #include "icinga/icingaapplication.h"
#include "icinga/checkresultmessage.h" #include "icinga/checkresultmessage.h"
#include "icinga/cib.h" #include "icinga/cib.h"
@ -38,9 +39,9 @@ const double Service::CheckIntervalDivisor = 5.0;
boost::signals2::signal<void (const Service::Ptr&)> Service::OnCheckerChanged; boost::signals2::signal<void (const Service::Ptr&)> Service::OnCheckerChanged;
boost::signals2::signal<void (const Service::Ptr&)> Service::OnNextCheckChanged; boost::signals2::signal<void (const Service::Ptr&)> Service::OnNextCheckChanged;
Value Service::GetCheckCommand(void) const CheckCommand::Ptr Service::GetCheckCommand(void) const
{ {
return m_CheckCommand; return CheckCommand::GetByName(m_CheckCommand);
} }
long Service::GetMaxCheckAttempts(void) const long Service::GetMaxCheckAttempts(void) const
@ -365,6 +366,8 @@ void Service::ProcessCheckResult(const Dictionary::Ptr& cr)
int state = cr->Get("state"); int state = cr->Get("state");
SetState(static_cast<ServiceState>(state)); SetState(static_cast<ServiceState>(state));
bool call_eventhandler = false;
if (old_state != GetState()) { if (old_state != GetState()) {
SetLastStateChange(now); SetLastStateChange(now);
@ -390,6 +393,8 @@ void Service::ProcessCheckResult(const Dictionary::Ptr& cr)
service->SetNextCheck(Utility::GetTime()); service->SetNextCheck(Utility::GetTime());
} }
} }
call_eventhandler = true;
} }
bool hardChange = (GetStateType() == StateTypeHard && old_stateType == StateTypeSoft); bool hardChange = (GetStateType() == StateTypeHard && old_stateType == StateTypeSoft);
@ -451,6 +456,9 @@ void Service::ProcessCheckResult(const Dictionary::Ptr& cr)
EndpointManager::GetInstance()->SendMulticastMessage(rm); EndpointManager::GetInstance()->SendMulticastMessage(rm);
if (call_eventhandler)
ExecuteEventHandler();
if (send_downtime_notification) if (send_downtime_notification)
RequestNotifications(in_downtime ? NotificationDowntimeStart : NotificationDowntimeEnd, cr); RequestNotifications(in_downtime ? NotificationDowntimeStart : NotificationDowntimeEnd, cr);
@ -549,13 +557,10 @@ void Service::ExecuteCheck(void)
Service::Ptr self = GetSelf(); Service::Ptr self = GetSelf();
std::vector<Value> arguments;
arguments.push_back(self);
Dictionary::Ptr result; Dictionary::Ptr result;
try { try {
result = InvokeMethod("check", arguments); result = GetCheckCommand()->Execute(GetSelf());
} catch (const std::exception& ex) { } catch (const std::exception& ex) {
std::ostringstream msgbuf; std::ostringstream msgbuf;
msgbuf << "Exception occured during check for service '" msgbuf << "Exception occured during check for service '"

View File

@ -0,0 +1,39 @@
/******************************************************************************
* Icinga 2 *
* Copyright (C) 2012 Icinga Development Team (http://www.icinga.org/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
* as published by the Free Software Foundation; either version 2 *
* of the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the Free Software Foundation *
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. *
******************************************************************************/
#include "icinga/service.h"
#include "icinga/eventcommand.h"
using namespace icinga;
EventCommand::Ptr Service::GetEventCommand(void) const
{
return EventCommand::GetByName(m_EventCommand);
}
void Service::ExecuteEventHandler(void)
{
EventCommand::Ptr ec = GetEventCommand();
if (!ec)
return;
Log(LogDebug, "icinga", "Executing event handler for service '" + GetName() + "'");
ec->Execute(GetSelf());
}

View File

@ -19,6 +19,7 @@
#include "icinga/service.h" #include "icinga/service.h"
#include "icinga/servicegroup.h" #include "icinga/servicegroup.h"
#include "icinga/checkcommand.h"
#include "icinga/icingaapplication.h" #include "icinga/icingaapplication.h"
#include "icinga/macroprocessor.h" #include "icinga/macroprocessor.h"
#include "config/configitembuilder.h" #include "config/configitembuilder.h"
@ -39,7 +40,6 @@ Service::Service(const Dictionary::Ptr& serializedObject)
RegisterAttribute("display_name", Attribute_Config, &m_DisplayName); RegisterAttribute("display_name", Attribute_Config, &m_DisplayName);
RegisterAttribute("macros", Attribute_Config, &m_Macros); RegisterAttribute("macros", Attribute_Config, &m_Macros);
RegisterAttribute("export_macros", Attribute_Config, &m_ExportMacros);
RegisterAttribute("hostdependencies", Attribute_Config, &m_HostDependencies); RegisterAttribute("hostdependencies", Attribute_Config, &m_HostDependencies);
RegisterAttribute("servicedependencies", Attribute_Config, &m_ServiceDependencies); RegisterAttribute("servicedependencies", Attribute_Config, &m_ServiceDependencies);
RegisterAttribute("servicegroups", Attribute_Config, &m_ServiceGroups); RegisterAttribute("servicegroups", Attribute_Config, &m_ServiceGroups);
@ -51,6 +51,8 @@ Service::Service(const Dictionary::Ptr& serializedObject)
RegisterAttribute("retry_interval", Attribute_Config, &m_RetryInterval); RegisterAttribute("retry_interval", Attribute_Config, &m_RetryInterval);
RegisterAttribute("checkers", Attribute_Config, &m_Checkers); RegisterAttribute("checkers", Attribute_Config, &m_Checkers);
RegisterAttribute("event_command", Attribute_Config, &m_EventCommand);
RegisterAttribute("next_check", Attribute_Replicated, &m_NextCheck); RegisterAttribute("next_check", Attribute_Replicated, &m_NextCheck);
RegisterAttribute("current_checker", Attribute_Replicated, &m_CurrentChecker); RegisterAttribute("current_checker", Attribute_Replicated, &m_CurrentChecker);
RegisterAttribute("check_attempt", Attribute_Replicated, &m_CheckAttempt); RegisterAttribute("check_attempt", Attribute_Replicated, &m_CheckAttempt);
@ -139,11 +141,6 @@ Dictionary::Ptr Service::GetMacros(void) const
return m_Macros; return m_Macros;
} }
Array::Ptr Service::GetExportMacros(void) const
{
return m_ExportMacros;
}
Array::Ptr Service::GetHostDependencies(void) const Array::Ptr Service::GetHostDependencies(void) const
{ {
return m_HostDependencies; return m_HostDependencies;
@ -386,7 +383,13 @@ bool Service::ResolveMacro(const String& macro, const Dictionary::Ptr& cr, Strin
*result = GetDisplayName(); *result = GetDisplayName();
return true; return true;
} else if (macro == "SERVICECHECKCOMMAND") { } else if (macro == "SERVICECHECKCOMMAND") {
*result = "check_i2"; CheckCommand::Ptr commandObj = GetCheckCommand();
if (commandObj)
*result = commandObj->GetName();
else
*result = "";
return true; return true;
} }

View File

@ -57,7 +57,8 @@ enum CommentType
CommentAcknowledgement = 4 CommentAcknowledgement = 4
}; };
class CheckResultMessage; class CheckCommand;
class EventCommand;
/** /**
* An Icinga service. * An Icinga service.
@ -84,7 +85,6 @@ public:
String GetDisplayName(void) const; String GetDisplayName(void) const;
Host::Ptr GetHost(void) const; Host::Ptr GetHost(void) const;
Dictionary::Ptr GetMacros(void) const; Dictionary::Ptr GetMacros(void) const;
Array::Ptr GetExportMacros(void) const;
Array::Ptr GetHostDependencies(void) const; Array::Ptr GetHostDependencies(void) const;
Array::Ptr GetServiceDependencies(void) const; Array::Ptr GetServiceDependencies(void) const;
Array::Ptr GetGroups(void) const; Array::Ptr GetGroups(void) const;
@ -101,7 +101,7 @@ public:
/* Checks */ /* Checks */
Array::Ptr GetCheckers(void) const; Array::Ptr GetCheckers(void) const;
Value GetCheckCommand(void) const; shared_ptr<CheckCommand> GetCheckCommand(void) const;
long GetMaxCheckAttempts(void) const; long GetMaxCheckAttempts(void) const;
TimePeriod::Ptr GetCheckPeriod(void) const; TimePeriod::Ptr GetCheckPeriod(void) const;
double GetCheckInterval(void) const; double GetCheckInterval(void) const;
@ -241,6 +241,10 @@ public:
void UpdateSlaveNotifications(void); void UpdateSlaveNotifications(void);
/* Event Handler */
void ExecuteEventHandler(void);
shared_ptr<EventCommand> GetEventCommand(void) const;
protected: protected:
virtual void OnRegistrationCompleted(void); virtual void OnRegistrationCompleted(void);
virtual void OnAttributeChanged(const String& name); virtual void OnAttributeChanged(const String& name);
@ -250,7 +254,6 @@ private:
Attribute<String> m_DisplayName; Attribute<String> m_DisplayName;
Attribute<Dictionary::Ptr> m_Macros; Attribute<Dictionary::Ptr> m_Macros;
Attribute<Array::Ptr> m_ExportMacros;
Attribute<Array::Ptr> m_HostDependencies; Attribute<Array::Ptr> m_HostDependencies;
Attribute<Array::Ptr> m_ServiceDependencies; Attribute<Array::Ptr> m_ServiceDependencies;
Attribute<Array::Ptr> m_ServiceGroups; Attribute<Array::Ptr> m_ServiceGroups;
@ -260,7 +263,7 @@ private:
Attribute<String> m_HostName; Attribute<String> m_HostName;
/* Checks */ /* Checks */
Attribute<Value> m_CheckCommand; Attribute<String> m_CheckCommand;
Attribute<long> m_MaxCheckAttempts; Attribute<long> m_MaxCheckAttempts;
Attribute<String> m_CheckPeriod; Attribute<String> m_CheckPeriod;
Attribute<double> m_CheckInterval; Attribute<double> m_CheckInterval;
@ -309,6 +312,9 @@ private:
Attribute<bool> m_ForceNextNotification; Attribute<bool> m_ForceNextNotification;
static void RefreshNotificationsCache(void); static void RefreshNotificationsCache(void);
/* Event Handler */
Attribute<String> m_EventCommand;
}; };
} }