<p>I did not get any feed back on my first nagios episode, so I can only assume that I perfectly explained what nagios is. And my installation instructions were so good, that no one had any questions. So I will move on to some additional nagios topics.</p>
<h2 id="why-use-nagios">Why use nagios</h2>
<p>One thing I meant to talk about but forgot in the intro is why you may want to run nagios as a hobbyist.</p>
<ul>
<li>Education, learning a new technology for fun</li>
<li>Network Monitoring is a valuable skill and benefit your career if you work in IT</li>
<li>Early warning for failing hardware</li>
<li>Monitoring self hosted applications</li>
<li>Notification for home security devices IP cameras</li>
</ul>
<p>Most of the benefits of nagios are not specific to nagios. There are plenty of other options for monitoring, and all of them are worth exploring.</p>
<h2 id="notification-options">Notification Options</h2>
<h3 id="email">Email</h3>
<p>I had planned on discussing how to set up postfix to send emails. But, that is such a big topic I will have to skip it. I will instead talk about what I do to send email. And Maybe you can do something similar.</p>
<p>Spammers have ruined the ability to directly send email. Most residential ISPs block port 25 outbound to prevent malware from sending email. Some Virtual hosting providers may not block sending mail, but many mail servers will not accept mail from VPS IP ranges.</p>
<p>There are a few ways to get around this problem. I use the email delivery service <code>Sendgrid</code>. They do all the work of staying off the list of spammers, and most email providers trust mail send via Sendgrid.</p>
<p>I wont go into the instructions for configuring postfix to relay outgoing mail via Sendgrid, but their documentation is easy to follow.</p>
<p>There are plenty of services like sendgrid. And most have a free tier. So unless you are blasting out alerts you probably will not have to pay. If you want to send alerts from nagios via email, I recommend finding a email sending service that works for you.</p>
<h3 id="push-alerts">Push alerts</h3>
<p>There are a few options (besides email) for getting alerts on your phone.</p>
<h4 id="anag">aNag</h4>
<p>The easiest way to get alerts is probably the <code>aNag</code> Android app. aNag connects to the nagios UI to get status updates. It can be configured to check in periodically and there generate notifications for failed checks.</p>
<p>One downside to aNag is the phone has to be able to connect to the nagios server. So, if nagios is on a private network, you will need a VPN when you are not on the same network.</p>
<p>If you decide to put nagios on a public network, be sure to configure apache to only use HTTPS. <code>certbot</code> makes this really easy.</p>
<h4 id="pushover">Pushover</h4>
<p>Another option is to us a Push Notification service that can send notifications that are triggered by API calls.</p>
<p>I like to use the pushover.net You pay $5 when you download the pushover app from the app store, and then notifications are sent for free. They offer a 30 day trial if you want to evaluate the service.</p>
<p>To use pushover, we will add a new contact to nagios. The command for the pushover contact is a script that calls the pushover API via curl.</p>
<p>Remember from the previous episode, nagios has a <code>conf.d</code> directory and will load any files in that directory. So we will create a new file <code>/etc/nagios4/conf.d/pushover.cfg</code> and restart nagios. The contents of the pushover file will be in the show notes.</p>
<p>To use pushover for specific checks, and the contact to that check. See the example in the show notes. Or if you want to use pushover for everything Modify the definitions for the host and service templates to use pushover as a contact</p>
<p>The script that calls the Pushover API is at <code>https://github.com/jedda/OSX-Monitoring-Tools/blob/master/notify_by_pushover.sh</code> Save a copy of the script in the nagios plugins directory.</p>
<p>pushover.cfg</p>
<pre><code># &#39;notify-host-pushover&#39; command definition

define command{
        command_name    notify-host-pushover
        command_line    $USER1$/notify_by_pushover.sh -u $CONTACTADDRESS1$ -a $CONTACTADDRESS2$ -c &#39;persistent&#39; -w &#39;siren&#39; -t &quot;Nagios&quot; -m &quot;$NOTIFICATIONTYPE$ Host $HOSTNAME$ $HOSTSTATE$&quot;
        }

# &#39;notify-service-pushover&#39; command definition

define command{
        command_name   notify-service-pushover
        command_line   $USER1$/notify_by_pushover.sh -u $CONTACTADDRESS1$ -a $CONTACTADDRESS2$ -c &#39;persistent&#39; -w &#39;siren&#39; -t &quot;Nagios&quot; -m &quot;$HOSTNAME$ $SERVICEDESC$ : $SERVICESTATE$ Additional info: $SERVICEOUTPUT$&quot;
        }

define contact{
        name                            generic-pushover
        host_notifications_enabled      1
        service_notifications_enabled   1
        host_notification_period        24x7
        service_notification_period     24x7
    service_notification_options    w,c,r
    host_notification_options       d,r
        host_notification_commands      notify-host-pushover
        service_notification_commands   notify-service-pushover
        can_submit_commands             1
        retain_status_information       1
        retain_nonstatus_information    1
        contact_name           Pushover
        address1               {{ pushover_user_key }}
        address2               {{ pushover_app_key }}
}</code></pre>
<h2 id="writing-custom-checks">writing custom checks</h2>
<p>One of the big advantages of nagios is the ability to write custom checks. In the previous episode, I mentioned that the status of the nagios checks are based on exit code.</p>
<table>
<thead>
<tr class="header">
<th>Exit Code</th>
<th>status</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td>0</td>
<td>OK/UP</td>
</tr>
<tr class="even">
<td>1</td>
<td>WARNING</td>
</tr>
<tr class="odd">
<td>2</td>
<td>CRITICAL</td>
</tr>
</tbody>
</table>
<p>So, to write a custom check, we need a script that will perform a check, and exit with an exit code based on the results of the check.</p>
<h3 id="verify-recent-log-entry">Verify recent log entry</h3>
<p>I have a server where occasionally the syslog daemon stop running,</p>
<p>Instead of trying to figure out why syslog keeps crashing, I wrote a script to check the log file is being updated. The script looks for the expected log file and tests that it has been modified in the last few minutes. The script will:</p>
<ul>
<li>exit 0 if the syslog file is less than 1 minute old</li>
<li>exit 1 if the syslog file is less than 10 minutes old</li>
<li>exit 2 if the syslog file is more that than 10 minutes old or does not exist</li>
</ul>
<p>Since the server with the crashy syslog is not the same server running nagios, I need a way for nagios to execute the script on the remote server.</p>
<p>Nagios has a few ways to run check commands on remote servers. I prefer to use ssh, but there are some disadvantages to using ssh. Specifically the resources required to establish the ssh connection can be heavier than some of the other remote execution methods.</p>
<p>The <code>check_by_ssh</code> plugin can be used to execute check commands on another system. Typically ssh-key authentication is set up so the user that is running the nagios daemon can log in to the remote system without a password</p>
<p>You can try the command to make sure it is working.</p>
<pre><code>cd /usr/lib/nagios/plugins
./check_by_ssh -H RemoteHost -u RemoteUser \
-C /path/to/remote/script/check_log_age.sh</code></pre>
<p>The new command can be added to a file in the nagios conf.d directory</p>
<pre><code>define command {
    command_name check_syslog_age
    command_line    $USER1$/check_by_ssh  -u RemoteUser -C /remote/path/check_log_age.sh
        }</code></pre>
<p>After adding the command definition, <code>check_syslog_age</code> can be added as a service check.</p>
<p>The Log Check script:</p>
<pre><code>#!/usr/bin/bash

TODAY=$(date +%Y%m%d)
LOGPATH=&quot;/syslog&quot;
TODAYSLOG=&quot;$TODAY.log&quot;
if test `find &quot;$LOGPATH/$TODAYSLOG&quot; -mmin -1`
then
    echo OK
    exit 0
elif test `find &quot;$LOGPATH/$TODAYSLOG&quot; -mmin -10`
then
    echo WARNING
    exit 1
else
    echo CRITICAL
    exit 2
fi</code></pre>
<h2 id="using-snmp-to-monitor-load-average-and-disk-usage">Using snmp to monitor load average and disk usage</h2>
<p>SNMP can get complicated and I have mixed feelings about using it. I am not going to go into the SNMP versions or the different authentication options for SNMP. But I will show a minimal setup that allows some performance data to be checked by nagios</p>
<p>The SNMP authentication that I am demonstrating is only appropriate for isolated networks. If you plan to use snmp over a public network, I recommend looking into more secure versions of SNMP or tunnelling the check traffic via ssh or a VPN.</p>
<p>If you want to learn more about SNMP, I recommend "SNMP Mastery" by Michael W Lucas. <a href="https://www.tiltedwindmillpress.com/product/snmp-mastery/" class="uri">https://www.tiltedwindmillpress.com/product/snmp-mastery/</a></p>
<h3 id="snmp-setup">SNMP setup</h3>
<p>First we need to configure the client to respond to SNMP request. On Ubuntu, <code>apt install snmpd</code></p>
<p>By default, snmpd listens on localhost. Replace the existing snmpd.conf with this example to set a read only community string and listen on all IP addresses.</p>
<p>And don't forget, I do not recommend this for a Public Network. Restart snmpd and open port 161 if there is a firewall enabled.</p>
<pre><code>agentAddress udp:161,udp6:[::1]:161
rocommunity NEW_SECURE_PASSWORD
disk /</code></pre>
<h3 id="snmp-nagios-checks">SNMP nagios checks</h3>
<p>The nagios plugin package installs several pre-defined snmp checks in <code>/etc/nagios-plugins/config/snmp.cfg</code> Look through the file to get an idea of the checks that can be performed via SNMP.</p>
<p>Below is an example of a client configuration that uses SNMP. If you look at how the command definitions, most of them have an option to accept arguments to modify how the check is done The argument placeholders re represented by <code>$ARG1$</code></p>
<p>In most cases, the arguments are optional. This particular SNMP check for disk space requires an argument to complete the disk ID being checked.</p>
<p>When the service check is defined, the arguments are separated by <code>!</code> You can also see in the example how you can</p>
<ul>
<li>add additional contacts</li>
<li>Change the check attempts - number or retires before sending an alert</li>
<li>Frequency of checks, the default is every 5 minutes</li>
</ul>
<pre><code>define host {
  host_name ServerIP
  use linux-server
}
define service {
  use generic-service
  host_name ServerIP
  contacts Pushover
  max_check_attempts 1
  check_interval 1
  service_description DISK
  check_command snmp_disk!NEW_SECURE_PASSWORD!1!1 # first arg is disk number
  # command in /etc/nagios-plugins/config/snmp.cfg
}
define service {
  use generic-service
  host_name ServerIP
  contacts Pushover
  service_description LOAD
  check_command snmp_load!NEW_SECURE_PASSWORD
  # command in /etc/nagios-plugins/config/snmp.cfg
}
define service {
  use generic-service
  host_name ServerIP
  service_description Memory
  check_command snmp_mem!NEW_SECURE_PASSWORD
  # command in /etc/nagios-plugins/config/snmp.cfg
}
define service {
  use generic-service
  host_name ServerIP
  service_description Swap
  check_command snmp_swap!NEW_SECURE_PASSWORD
  # command in /etc/nagios-plugins/config/snmp.cfg
}</code></pre>
<h3 id="check-servers-for-updates">Check servers for updates</h3>
<p>Nagios has plugins that can check if there are system updates required.</p>
<ul>
<li>Number of updates</li>
<li>Check will be CRITICAL if any of the updates are security related.</li>
<li>Is a reboot required to load the latest kernel.</li>
</ul>
<p>The check plugin is installed on the remote server. The plugin for Debian based systems is <code>nagios-plugins-contrib</code> or <code>nagios-plugins-check-updates</code> for Red Hat based systems.</p>
<p>The command definitions are below. Since the plugins take longer to run, you will probably need to modify the nagios plugin timeout.</p>
<pre><code>define command {
    command_name check_yum
        command_line    $USER1$/check_by_ssh -H $HOSTADDRESS$ -t 120 -u root -C &quot;/usr/lib64/nagios/plugins/check_updates -t120&quot;
    }
define command {
       command_name check_apt
       command_line    $USER1$/check_by_ssh -H $HOSTADDRESS$ -t 120 -u nagios-ssh -C &quot;/usr/lib/nagios/plugins/check_apt -t60&quot;
        }</code></pre>
<p>That's probably all the nagios I can handle for now. Leave a comment if there are nagios topics you would like to hear about. Thanks for listening and I will see you next time.</p>
