Take the 2-minute tour ×
Server Fault is a question and answer site for system and network administrators. It's 100% free, no registration required.

I'm trying to setup Nagios to monitor my various machines using hostgroups to define 'machine roles', against which I run services to check the machines by role. However, I'd like to use conditional operators that would enable me to run the service check against an intersection of two host groups, rather than their unions... i.e. using &&, ||, or () operators.

For example, imagine I have the following servers:

  • www-eu: Linux WWW (Apache) server, in the EU
  • www-us: Windows WWW (IIS) server, in the US (West coast)
  • ftp-eu: Linux FTP server, in the EU
  • ftp-us: Windows FTP server, in the US

I would want to create the following host groups:

  • US-Servers: www-us, ftp-us
  • EU-Servers: www-eu, ftp-eu
  • WWW-Servers: www-us, www-eu
  • FTP-Servers: ftp-us, ftp-eu

Now say I'm interested in checking the HTTP response time for my web servers. Then let's say this particular Nagios service is running from the US (West Coast), and that I have a command called *check_http_response_time*. This command will check the responsiveness of the HTTP server, which I can provide an argument which defines the max response time before raising critical.

My command might look like: check_http_response_time $HOSTNAME$ 50

Now traditionally, I can run my checks by specifying a list of host or hostgroups.

define service{
    use             local-service
    hostgroup_name              WWW-Servers   # Servers = www-us, www-eu
    servicegroups           WWW Checks
    service_description     Check HTTP Response Time
    check_command           check_http_response_time!50
}

However, with the above service definition, given my Nagios service is in US West, I could reasonably expect that my EU server will return critical. Really, I want different thresholds for each region (50 for US West, 200 for EU.)

To accomplish this, I would have to permutate my service for each host and set a custom threshold for each, or alternatively permutate out my service groups by role & region (i.e. WWW-Servers-EU), and run specific thresholds against those. Though the latter is better, both are much messier than I'd like...

What I would love, and what this post is asking for, is a way to use hostgroups to perform an intersection using conditional logic, rather than a simple union. It might look like:

define service{
    use             local-service
    hostgroup_name              WWW-Servers && US-Servers
    servicegroups           WWW Checks
    service_description     Check HTTP Response Time
    check_command           check_http_response_time!50
}

It then would run the check only against servers that are in both WWW-Servers and US-Servers hostgroups: in my example, just www-us. The benefits of such a feature would be significant for Nagios services configured for large-scale.

Is this feature available? If it isn't, will it be available in the future? Is there an alternative way to accomplish this given the most recent Nagios version?

Any tips/suggestions are most appreciated!

  • Dave
share|improve this question

3 Answers 3

up vote 6 down vote accepted

It then would run the check only against servers that are in both WWW-Servers and US-Servers, in my example, just www-us.

Is this feature available? If it isn't, will it be available in the future?

Ethan Galstad said that he doesn't have any plans to add intersection support.

Is there an alternative way to accomplish this given the most recent Nagios version?

You can exclude some hosts from the definition by preceding the host or hostgroup with a ! symbol. So, try something like this:

define service{
    use                     local-service
    hostgroup_name          *,!EU-Servers,!FTP-Servers
    servicegroups           WWW Checks
    service_description     Check HTTP Response Time
    check_command           check_http_response_time!50
}
share|improve this answer
    
This is precisely the kind of answer I was looking for, thank you! –  Dave Oct 9 '12 at 15:43

My method depends on what I'm trying to achieve. Normally I'm a believer in more hostgroups are a good thing but I also believe in automating the Nagios Configuration with scripts whenever possible.

To handle your use case however, I would write a handler that takes a list of the host group membership using the $HOSTGROUPNAMES$ macro and parsing the command string appropriately.

$HOSTGROUPNAMES$ is described in the Nagios Documentation. It provides a comma separated list of hostgroups the host is a member of. Parsing the command line should be simple using most scripting languages.

The command config could look like

check_http_by_hostgroup -g $HOSTGROUPNAMES$ -H $HOSTNAME -I $HOSTADDRESS$ -U $ARG1$ -W $ARG2$ -C $ARG3$

and the service config could look like:

define service{
    use            local-service
    hostgroup_name WWW-Servers ; hosts are also members of us, eu, or ap
    servicegroups  WWW Checks
    service_description  Check HTTP Response Time
    check_command  check_http_by_hostgroup|http://foo.bar/|us=30,eu=160|us=90,eu=240,ap=390
}

Then define host-group membership in the host configs rather than in the host-group config.

share|improve this answer
    
Interesting way of handling it. Seems a little messy at scale though. For example, imagine I have 50 hosting regions... this call would get really long, even though it would still work. –  Dave Oct 9 '12 at 15:47

You might want to look at the service/host dependancy capability in Nagios.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.