diff --git a/README.md b/README.md index 960c5caa..e9b3d4cc 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,35 @@ -This is the repository for all user contributed stuff +# This is the repository for all user contributed stuff -* contrib/tools/ is for 3rd-party tools. It usually serves as an incubator of trunk/contrib. -* contrib/plugins/ is for 3rd-party plugins. It will serve as the backend of exchange.munin-monitoring.org when it is operational again. -* contrib/templates/ is for 3rd-party templates. Feel free to update templates, or even to create new ones. Bonus points for mobile-friendly ones :) +## contrib/plugins/ - 3rd-party plugins + +**This is usually where you want to begin your journey.** + +Here you'll find all the plugins coming from http://exchange.munin-monitoring.org/. +That web site is for the time being disabled, new updates are done here. + +If a dedicated website comes back alive, its plugin backend will be this git repo. + +## contrib/templates/ - 3rd-party templates + +Feel free to update templates here, or even to create new ones. + +Bonus points for mobile-friendly ones :) + +Note that the one named `official` is a loose-synced copy of the one in SVN trunk. +It should serves as a base for small editions that can be resynced in SVN trunk, so for that : + +* don't copy the whole template +* directly edit files in this directory + +## contrib/tools/ - 3rd-party tools + +Here, you can put just any kind of tool. Please use this directory instead of a random place on the internet. +It makes things way more easy to search for others. + +And, it serves as an incubator of SVN `trunk/contrib` :-) + +## Notes to contributors + +We like to have ''elementary'' commits (a good rationale is : one per Changelog entry), as it is much easier to manage for reviewing. Debugging is also usually easier that way. + +So please **don't** be afraid to make as many commits as needed. diff --git a/images/snmp__fn-cpu.png b/images/snmp__fn-cpu.png new file mode 100755 index 00000000..a2f50b0d Binary files /dev/null and b/images/snmp__fn-cpu.png differ diff --git a/images/snmp__fn-memory.png b/images/snmp__fn-memory.png new file mode 100755 index 00000000..19846583 Binary files /dev/null and b/images/snmp__fn-memory.png differ diff --git a/images/snmp__fn-sessions.png b/images/snmp__fn-sessions.png new file mode 100755 index 00000000..e6a6153e Binary files /dev/null and b/images/snmp__fn-sessions.png differ diff --git a/images/snmp__fn-vpnsessions.png b/images/snmp__fn-vpnsessions.png new file mode 100755 index 00000000..a087874c Binary files /dev/null and b/images/snmp__fn-vpnsessions.png differ diff --git a/plugins/other/amule_queue b/plugins/amule/amule_queue similarity index 100% rename from plugins/other/amule_queue rename to plugins/amule/amule_queue diff --git a/plugins/other/amule_shares b/plugins/amule/amule_shares similarity index 100% rename from plugins/other/amule_shares rename to plugins/amule/amule_shares diff --git a/plugins/other/amule_transfers b/plugins/amule/amule_transfers similarity index 100% rename from plugins/other/amule_transfers rename to plugins/amule/amule_transfers diff --git a/plugins/other/amule_uptime b/plugins/amule/amule_uptime similarity index 100% rename from plugins/other/amule_uptime rename to plugins/amule/amule_uptime diff --git a/plugins/other/apache_activity b/plugins/apache/apache_activity similarity index 100% rename from plugins/other/apache_activity rename to plugins/apache/apache_activity diff --git a/plugins/other/apache_average_time_last_n_requests b/plugins/apache/apache_average_time_last_n_requests similarity index 100% rename from plugins/other/apache_average_time_last_n_requests rename to plugins/apache/apache_average_time_last_n_requests diff --git a/plugins/other/apache_request_rate b/plugins/apache/apache_request_rate similarity index 100% rename from plugins/other/apache_request_rate rename to plugins/apache/apache_request_rate diff --git a/plugins/other/apache_smaps b/plugins/apache/apache_smaps similarity index 100% rename from plugins/other/apache_smaps rename to plugins/apache/apache_smaps diff --git a/plugins/other/apache_users b/plugins/apache/apache_users similarity index 100% rename from plugins/other/apache_users rename to plugins/apache/apache_users diff --git a/plugins/other/apache_watch_ b/plugins/apache/apache_watch_ similarity index 100% rename from plugins/other/apache_watch_ rename to plugins/apache/apache_watch_ diff --git a/plugins/other/eaccelerator b/plugins/apache/eaccelerator similarity index 100% rename from plugins/other/eaccelerator rename to plugins/apache/eaccelerator diff --git a/plugins/other/http-response-times b/plugins/apache/http-response-times similarity index 100% rename from plugins/other/http-response-times rename to plugins/apache/http-response-times diff --git a/plugins/other/php-cgi b/plugins/apache/php-cgi similarity index 100% rename from plugins/other/php-cgi rename to plugins/apache/php-cgi diff --git a/plugins/other/php_eaccelerator b/plugins/apache/php_eaccelerator similarity index 100% rename from plugins/other/php_eaccelerator rename to plugins/apache/php_eaccelerator diff --git a/plugins/other/php_sessions b/plugins/apache/php_sessions similarity index 100% rename from plugins/other/php_sessions rename to plugins/apache/php_sessions diff --git a/plugins/other/apt-proxy b/plugins/apt/apt-proxy similarity index 100% rename from plugins/other/apt-proxy rename to plugins/apt/apt-proxy diff --git a/plugins/other/asterisk_inuse b/plugins/asterisk/asterisk_inuse similarity index 100% rename from plugins/other/asterisk_inuse rename to plugins/asterisk/asterisk_inuse diff --git a/plugins/other/asterisk_sippeers b/plugins/asterisk/asterisk_sippeers similarity index 100% rename from plugins/other/asterisk_sippeers rename to plugins/asterisk/asterisk_sippeers diff --git a/plugins/other/portaudit b/plugins/audit/portaudit similarity index 100% rename from plugins/other/portaudit rename to plugins/audit/portaudit diff --git a/plugins/other/bacula_job b/plugins/bacula/bacula_job similarity index 100% rename from plugins/other/bacula_job rename to plugins/bacula/bacula_job diff --git a/plugins/other/bacula_sd b/plugins/bacula/bacula_sd similarity index 100% rename from plugins/other/bacula_sd rename to plugins/bacula/bacula_sd diff --git a/plugins/other/boinc_credit b/plugins/boinc/boinc_credit similarity index 100% rename from plugins/other/boinc_credit rename to plugins/boinc/boinc_credit diff --git a/plugins/other/boinc_estwk b/plugins/boinc/boinc_estwk similarity index 100% rename from plugins/other/boinc_estwk rename to plugins/boinc/boinc_estwk diff --git a/plugins/other/boinc_projs b/plugins/boinc/boinc_projs similarity index 100% rename from plugins/other/boinc_projs rename to plugins/boinc/boinc_projs diff --git a/plugins/other/boinc_wus b/plugins/boinc/boinc_wus similarity index 100% rename from plugins/other/boinc_wus rename to plugins/boinc/boinc_wus diff --git a/plugins/other/cacti-host b/plugins/cacti/cacti-host similarity index 100% rename from plugins/other/cacti-host rename to plugins/cacti/cacti-host diff --git a/plugins/other/cacti_poller_time b/plugins/cacti/cacti_poller_time similarity index 100% rename from plugins/other/cacti_poller_time rename to plugins/cacti/cacti_poller_time diff --git a/plugins/other/cacti_rrds b/plugins/cacti/cacti_rrds similarity index 100% rename from plugins/other/cacti_rrds rename to plugins/cacti/cacti_rrds diff --git a/plugins/other/celery_tasks b/plugins/celery/celery_tasks similarity index 100% rename from plugins/other/celery_tasks rename to plugins/celery/celery_tasks diff --git a/plugins/other/celery_tasks-2 b/plugins/celery/celery_tasks-2 similarity index 100% rename from plugins/other/celery_tasks-2 rename to plugins/celery/celery_tasks-2 diff --git a/plugins/other/dell_fans b/plugins/chassis/dell_fans similarity index 100% rename from plugins/other/dell_fans rename to plugins/chassis/dell_fans diff --git a/plugins/other/munin-plugin-for-cherokee b/plugins/cherokee/munin-plugin-for-cherokee similarity index 100% rename from plugins/other/munin-plugin-for-cherokee rename to plugins/cherokee/munin-plugin-for-cherokee diff --git a/plugins/other/condor_activity_ b/plugins/condor/condor_activity_ similarity index 100% rename from plugins/other/condor_activity_ rename to plugins/condor/condor_activity_ diff --git a/plugins/other/condor_ops_ b/plugins/condor/condor_ops_ similarity index 100% rename from plugins/other/condor_ops_ rename to plugins/condor/condor_ops_ diff --git a/plugins/other/condor_queue_ b/plugins/condor/condor_queue_ similarity index 100% rename from plugins/other/condor_queue_ rename to plugins/condor/condor_queue_ diff --git a/plugins/other/condor_states_ b/plugins/condor/condor_states_ similarity index 100% rename from plugins/other/condor_states_ rename to plugins/condor/condor_states_ diff --git a/plugins/other/dovecot126 b/plugins/correo/dovecot126 similarity index 100% rename from plugins/other/dovecot126 rename to plugins/correo/dovecot126 diff --git a/plugins/other/cpanp_o b/plugins/cpan/cpanp_o similarity index 100% rename from plugins/other/cpanp_o rename to plugins/cpan/cpanp_o diff --git a/plugins/other/currentcost b/plugins/currentcost/currentcost similarity index 100% rename from plugins/other/currentcost rename to plugins/currentcost/currentcost diff --git a/plugins/other/cyrus-imapd b/plugins/cyrus/cyrus-imapd similarity index 100% rename from plugins/other/cyrus-imapd rename to plugins/cyrus/cyrus-imapd diff --git a/plugins/other/df_abs_bsd b/plugins/disk/df_abs_bsd similarity index 100% rename from plugins/other/df_abs_bsd rename to plugins/disk/df_abs_bsd diff --git a/plugins/other/df_bsd b/plugins/disk/df_bsd similarity index 100% rename from plugins/other/df_bsd rename to plugins/disk/df_bsd diff --git a/plugins/other/df_with_nfs b/plugins/disk/df_with_nfs similarity index 100% rename from plugins/other/df_with_nfs rename to plugins/disk/df_with_nfs diff --git a/plugins/other/dirsizes b/plugins/disk/dirsizes similarity index 100% rename from plugins/other/dirsizes rename to plugins/disk/dirsizes diff --git a/plugins/other/du b/plugins/disk/du similarity index 100% rename from plugins/other/du rename to plugins/disk/du diff --git a/plugins/other/du-2 b/plugins/disk/du-2 similarity index 100% rename from plugins/other/du-2 rename to plugins/disk/du-2 diff --git a/plugins/other/du_multidirs b/plugins/disk/du_multidirs similarity index 100% rename from plugins/other/du_multidirs rename to plugins/disk/du_multidirs diff --git a/plugins/other/freedisk b/plugins/disk/freedisk similarity index 100% rename from plugins/other/freedisk rename to plugins/disk/freedisk diff --git a/plugins/other/iostat b/plugins/disk/iostat similarity index 100% rename from plugins/other/iostat rename to plugins/disk/iostat diff --git a/plugins/other/iostat-xfrs b/plugins/disk/iostat-xfrs similarity index 100% rename from plugins/other/iostat-xfrs rename to plugins/disk/iostat-xfrs diff --git a/plugins/other/linux_diskstat_ b/plugins/disk/linux_diskstat_ similarity index 100% rename from plugins/other/linux_diskstat_ rename to plugins/disk/linux_diskstat_ diff --git a/plugins/other/linux_diskstats_ b/plugins/disk/linux_diskstats_ similarity index 100% rename from plugins/other/linux_diskstats_ rename to plugins/disk/linux_diskstats_ diff --git a/plugins/other/log_sizes b/plugins/disk/log_sizes similarity index 100% rename from plugins/other/log_sizes rename to plugins/disk/log_sizes diff --git a/plugins/other/lvm_ b/plugins/disk/lvm_ similarity index 100% rename from plugins/other/lvm_ rename to plugins/disk/lvm_ diff --git a/plugins/other/lvm_snap_used b/plugins/disk/lvm_snap_used similarity index 56% rename from plugins/other/lvm_snap_used rename to plugins/disk/lvm_snap_used index cfcdc241..87574a24 100755 --- a/plugins/other/lvm_snap_used +++ b/plugins/disk/lvm_snap_used @@ -14,17 +14,19 @@ #%# capabilities=autoconf # # 2011/05/20 - pmoranga - initial version +# +# 2012/01/27 - Sébastien Gross +# - Fix lvdisplay path + +lvdisplay=$(which lvdisplay) if [ "$1" = "autoconf" ]; then - /usr/sbin/lvdisplay 2>/dev/null >/dev/null - if [ $? -eq 0 ] - then - echo yes - exit 0 - else - echo "no lvdisplay found" - fi - exit 1 + if test -n "${lvdisplay}"; then + echo yes + exit 0 + fi + echo "no lvdisplay found" + exit 1 fi @@ -34,9 +36,9 @@ if [ "$1" = "config" ]; then echo 'graph_vlabel %' echo 'graph_category disk' echo 'graph_args --base 100' - /usr/sbin/lvdisplay -C | awk '$3 ~ /^s/{print $1".label "$1" snapshot of "$5} ' + ${lvdisplay} -C | awk '$3 ~ /^s/{print $1".label "$1" snapshot of "$5} ' exit 0 fi -/usr/sbin/lvdisplay -C | awk '$3 ~ /^s/{print $1".value",int($6)} ' +${lvdisplay} -C | awk '$3 ~ /^s/{print $1".value",int($6)} ' diff --git a/plugins/other/lvm_usage b/plugins/disk/lvm_usage similarity index 100% rename from plugins/other/lvm_usage rename to plugins/disk/lvm_usage diff --git a/plugins/other/md_iostat_ b/plugins/disk/md_iostat_ similarity index 100% rename from plugins/other/md_iostat_ rename to plugins/disk/md_iostat_ diff --git a/plugins/other/megaraid-controller-information b/plugins/disk/megaraid-controller-information similarity index 100% rename from plugins/other/megaraid-controller-information rename to plugins/disk/megaraid-controller-information diff --git a/plugins/other/raid b/plugins/disk/raid similarity index 100% rename from plugins/other/raid rename to plugins/disk/raid diff --git a/plugins/other/raid-mismatch-count b/plugins/disk/raid-mismatch-count similarity index 100% rename from plugins/other/raid-mismatch-count rename to plugins/disk/raid-mismatch-count diff --git a/plugins/other/scsi_queue b/plugins/disk/scsi_queue similarity index 100% rename from plugins/other/scsi_queue rename to plugins/disk/scsi_queue diff --git a/plugins/other/smart b/plugins/disk/smart similarity index 100% rename from plugins/other/smart rename to plugins/disk/smart diff --git a/plugins/other/smart-by-id_ b/plugins/disk/smart-by-id_ similarity index 100% rename from plugins/other/smart-by-id_ rename to plugins/disk/smart-by-id_ diff --git a/plugins/other/smart_ b/plugins/disk/smart_ similarity index 100% rename from plugins/other/smart_ rename to plugins/disk/smart_ diff --git a/plugins/other/snmp__netapp_diskusage_ b/plugins/disk/snmp__netapp_diskusage_ similarity index 100% rename from plugins/other/snmp__netapp_diskusage_ rename to plugins/disk/snmp__netapp_diskusage_ diff --git a/plugins/other/snmp__netapp_inodeusage_ b/plugins/disk/snmp__netapp_inodeusage_ similarity index 100% rename from plugins/other/snmp__netapp_inodeusage_ rename to plugins/disk/snmp__netapp_inodeusage_ diff --git a/plugins/other/snmp__swap b/plugins/disk/snmp__swap similarity index 100% rename from plugins/other/snmp__swap rename to plugins/disk/snmp__swap diff --git a/plugins/other/xfs_frag b/plugins/disk/xfs_frag similarity index 100% rename from plugins/other/xfs_frag rename to plugins/disk/xfs_frag diff --git a/plugins/other/drbd b/plugins/drbd/drbd similarity index 100% rename from plugins/other/drbd rename to plugins/drbd/drbd diff --git a/plugins/other/drbd-stat b/plugins/drbd/drbd-stat similarity index 100% rename from plugins/other/drbd-stat rename to plugins/drbd/drbd-stat diff --git a/plugins/other/dspam_ b/plugins/dspam/dspam_ similarity index 100% rename from plugins/other/dspam_ rename to plugins/dspam/dspam_ diff --git a/plugins/other/dspam_activity b/plugins/dspam/dspam_activity similarity index 100% rename from plugins/other/dspam_activity rename to plugins/dspam/dspam_activity diff --git a/plugins/other/femon b/plugins/dvb/femon similarity index 100% rename from plugins/other/femon rename to plugins/dvb/femon diff --git a/plugins/other/hadoop-under_replicated-blocks b/plugins/dxtv/hadoop-under_replicated-blocks similarity index 100% rename from plugins/other/hadoop-under_replicated-blocks rename to plugins/dxtv/hadoop-under_replicated-blocks diff --git a/plugins/other/ejabberd_ b/plugins/ejabberd/ejabberd_ similarity index 99% rename from plugins/other/ejabberd_ rename to plugins/ejabberd/ejabberd_ index 0fee887e..b7757d42 100755 --- a/plugins/other/ejabberd_ +++ b/plugins/ejabberd/ejabberd_ @@ -43,7 +43,6 @@ shopt -s extglob EJCTL=$(which ejabberdctl) EJVER=$($EJCTL status | awk '/^ejabberd / {print $2}') -MUNIN_DEBUG=${MUNIN_DEBUG:-0} if [ "$1" == "autoconf" ]; then if [ -x $EJCTL > /dev/null ]; then diff --git a/plugins/other/hplog_f-a-hp-proliant-server-fans-speed b/plugins/environment/hplog_f-a-hp-proliant-server-fans-speed similarity index 100% rename from plugins/other/hplog_f-a-hp-proliant-server-fans-speed rename to plugins/environment/hplog_f-a-hp-proliant-server-fans-speed diff --git a/plugins/other/hplog_t-a-hp-proliant-server-temperatures b/plugins/environment/hplog_t-a-hp-proliant-server-temperatures similarity index 100% rename from plugins/other/hplog_t-a-hp-proliant-server-temperatures rename to plugins/environment/hplog_t-a-hp-proliant-server-temperatures diff --git a/plugins/other/alertme_keyfobsathome b/plugins/environmental/alertme_keyfobsathome similarity index 100% rename from plugins/other/alertme_keyfobsathome rename to plugins/environmental/alertme_keyfobsathome diff --git a/plugins/other/alertme_power b/plugins/environmental/alertme_power similarity index 100% rename from plugins/other/alertme_power rename to plugins/environmental/alertme_power diff --git a/plugins/other/esxi b/plugins/esx/esxi similarity index 100% rename from plugins/other/esxi rename to plugins/esx/esxi diff --git a/plugins/other/faxstat b/plugins/fax/faxstat similarity index 100% rename from plugins/other/faxstat rename to plugins/fax/faxstat diff --git a/plugins/other/zfs_cache_efficiency b/plugins/filesystem/zfs_cache_efficiency similarity index 100% rename from plugins/other/zfs_cache_efficiency rename to plugins/filesystem/zfs_cache_efficiency diff --git a/plugins/other/zfsarcstats-counters b/plugins/filesystem/zfsarcstats-counters similarity index 100% rename from plugins/other/zfsarcstats-counters rename to plugins/filesystem/zfsarcstats-counters diff --git a/plugins/other/firebird b/plugins/firebird/firebird similarity index 100% rename from plugins/other/firebird rename to plugins/firebird/firebird diff --git a/plugins/other/vbulletin_users b/plugins/forum/vbulletin_users similarity index 100% rename from plugins/other/vbulletin_users rename to plugins/forum/vbulletin_users diff --git a/plugins/other/punbb_users b/plugins/forums/punbb_users similarity index 100% rename from plugins/other/punbb_users rename to plugins/forums/punbb_users diff --git a/plugins/other/proftpd b/plugins/ftp/proftpd similarity index 100% rename from plugins/other/proftpd rename to plugins/ftp/proftpd diff --git a/plugins/other/proftpd_bytes b/plugins/ftp/proftpd_bytes similarity index 100% rename from plugins/other/proftpd_bytes rename to plugins/ftp/proftpd_bytes diff --git a/plugins/other/proftpd_count b/plugins/ftp/proftpd_count similarity index 100% rename from plugins/other/proftpd_count rename to plugins/ftp/proftpd_count diff --git a/plugins/other/pure-ftpd b/plugins/ftp/pure-ftpd similarity index 100% rename from plugins/other/pure-ftpd rename to plugins/ftp/pure-ftpd diff --git a/plugins/other/pureftpd_count b/plugins/ftp/pureftpd_count similarity index 100% rename from plugins/other/pureftpd_count rename to plugins/ftp/pureftpd_count diff --git a/plugins/other/vsftpd b/plugins/ftp/vsftpd similarity index 100% rename from plugins/other/vsftpd rename to plugins/ftp/vsftpd diff --git a/plugins/other/vsftpd-rel b/plugins/ftp/vsftpd-rel similarity index 100% rename from plugins/other/vsftpd-rel rename to plugins/ftp/vsftpd-rel diff --git a/plugins/other/denon_x311_volume b/plugins/funkytown/denon_x311_volume similarity index 100% rename from plugins/other/denon_x311_volume rename to plugins/funkytown/denon_x311_volume diff --git a/plugins/other/b3error_ b/plugins/games/b3error_ similarity index 100% rename from plugins/other/b3error_ rename to plugins/games/b3error_ diff --git a/plugins/other/cstat b/plugins/games/cstat similarity index 100% rename from plugins/other/cstat rename to plugins/games/cstat diff --git a/plugins/other/qstat b/plugins/games/qstat similarity index 100% rename from plugins/other/qstat rename to plugins/games/qstat diff --git a/plugins/other/qstatet_ b/plugins/games/qstatet_ similarity index 100% rename from plugins/other/qstatet_ rename to plugins/games/qstatet_ diff --git a/plugins/other/qstatqw_ b/plugins/games/qstatqw_ similarity index 100% rename from plugins/other/qstatqw_ rename to plugins/games/qstatqw_ diff --git a/plugins/other/geowebcache-bandwidth b/plugins/geowebcache/geowebcache-bandwidth similarity index 100% rename from plugins/other/geowebcache-bandwidth rename to plugins/geowebcache/geowebcache-bandwidth diff --git a/plugins/other/geowebcache-blankitems b/plugins/geowebcache/geowebcache-blankitems similarity index 100% rename from plugins/other/geowebcache-blankitems rename to plugins/geowebcache/geowebcache-blankitems diff --git a/plugins/other/geowebcache-cache-hits-ratio b/plugins/geowebcache/geowebcache-cache-hits-ratio similarity index 100% rename from plugins/other/geowebcache-cache-hits-ratio rename to plugins/geowebcache/geowebcache-cache-hits-ratio diff --git a/plugins/other/googlecode b/plugins/google/googlecode similarity index 100% rename from plugins/other/googlecode rename to plugins/google/googlecode diff --git a/plugins/other/nvidia_smi_ b/plugins/gpu/nvidia_smi_ similarity index 100% rename from plugins/other/nvidia_smi_ rename to plugins/gpu/nvidia_smi_ diff --git a/plugins/other/snmp__gwia_msgs_ b/plugins/groupwise/snmp__gwia_msgs_ similarity index 100% rename from plugins/other/snmp__gwia_msgs_ rename to plugins/groupwise/snmp__gwia_msgs_ diff --git a/plugins/other/snmp__gwmta_msgs_ b/plugins/groupwise/snmp__gwmta_msgs_ similarity index 100% rename from plugins/other/snmp__gwmta_msgs_ rename to plugins/groupwise/snmp__gwmta_msgs_ diff --git a/plugins/gunicorn/gunicorn_memory_status b/plugins/gunicorn/gunicorn_memory_status new file mode 100755 index 00000000..49e8719c --- /dev/null +++ b/plugins/gunicorn/gunicorn_memory_status @@ -0,0 +1,98 @@ +#!/usr/bin/env python +""" + gunicorn_status - A munin plugin for Linux to monitor the memory + usage of gunicorn processes + + Copyright (C) 2012 Azavea, Inc. + Author: Andrew Jennings + + Like Munin, this plugin is licensed under the GNU GPL v2 license + http://www.opensource.org/licenses/GPL-2.0 + + If you've put your gunicorn pid somewhere other than the + default /var/run/gunicorn.pid, you can add a section like + this to your munin-node's plugin configuration: + + [gunicorn_*] + env.gunicorn_pid_path [path to your gunicorn pid] + + This plugin supports the following munin configuration parameters: + #%# family=auto contrib + #%# capabilities=autoconf + +""" + +import sys, os +from subprocess import check_output + +# set path to your gunicorn pid +try: + GUNICORN_PID_PATH = os.environ['gunicorn_pid_path'] +except: + GUNICORN_PID_PATH = "/var/run/gunicorn.pid" + + +class GunicornMemoryStatus(): + master_pid = '' + """ + The Gunicorn master process pid, as a string + """ + + def __init__(self): + try: + self._get_master_pid() + except: + raise Exception("Couldn't read gunicorn pid information") + + + def print_total_memory(self): + print ('total_memory.value %d' % self._get_total_memory()) + + + def _get_master_pid(self): + master_pid_file = open(GUNICORN_PID_PATH) + self.master_pid = master_pid_file.read().rstrip() + master_pid_file.close() + return True + + def _get_total_memory(self): + master = self._get_master_memory() + total = master +self. _get_worker_memory() + total_in_mb = total / 1024 + return total_in_mb + + def _get_master_memory(self): + master = int(check_output( + ['ps', '--pid', self.master_pid, '-o', 'rss', '--no-headers'])) + return master + + def _get_worker_memory(self): + worker_processes = check_output( + ['ps', '--ppid', self.master_pid, '-o', 'rss', '--no-headers']) + process_memory_usage = [int(rss) for rss in worker_processes.splitlines()] + worker_memory_usage = sum(process_memory_usage) + return worker_memory_usage + +def print_config(): + print "graph_title Gunicorn - Memory Usage" + print "graph_args --base 1024 -l 0" + print "graph_vlabel Megabytes" + print "graph_category gunicorn" + print "total_memory.label Total Memory" + +if __name__ == "__main__": + if len(sys.argv) == 2 and sys.argv[1] == 'config': + print_config() + elif len(sys.argv) == 2 and sys.argv[1] == 'autoconf': + try: + open(GUNICORN_PID_PATH).close() + print "yes" + except: + print "no" + # Some docs say it'll be called with fetch, some say no arg at all + elif len(sys.argv) == 1 or (len(sys.argv) == 2 and sys.argv[1] == 'fetch'): + try: + status = GunicornMemoryStatus() + status.print_total_memory() + except: + sys.exit("Couldn't retrieve gunicorn memory usage information") diff --git a/plugins/gunicorn/gunicorn_status b/plugins/gunicorn/gunicorn_status new file mode 100755 index 00000000..2c9fc888 --- /dev/null +++ b/plugins/gunicorn/gunicorn_status @@ -0,0 +1,113 @@ +#!/usr/bin/env python +""" + gunicorn_status - A munin plugin for Linux to monitor gunicorn processes + + Copyright (C) 2012 Azavea, Inc. + Author: Andrew Jennings + + Like Munin, this plugin is licensed under the GNU GPL v2 license + http://www.opensource.org/licenses/GPL-2.0 + + If you've put your gunicorn pid somewhere other than the + default /var/run/gunicorn.pid, you can add a section like + this to your munin-node's plugin configuration: + + [gunicorn_*] + env.gunicorn_pid_path [path to your gunicorn pid] + + This plugin supports the following munin configuration parameters: + #%# family=auto contrib + #%# capabilities=autoconf + +""" + +import sys, os +from subprocess import check_output +from time import sleep + +# set path to your gunicorn pid +try: + GUNICORN_PID_PATH = os.environ['gunicorn_pid_path'] +except: + GUNICORN_PID_PATH = "/var/run/gunicorn.pid" + +class GunicornStatus(): + master_pid = '' + """ + The gunicorn master process pid, as a string + """ + + worker_pids = '' + """ + The list of gunicorn processes as strings + """ + + def __init__(self): + try: + self._get_master_pid() + self._get_worker_pids(self.master_pid) + except: + sys.exit("Couldn't read gunicorn pid") + + def print_total_workers(self): + print ('total_workers.value %d' % self._worker_count()) + + def print_idle_workers(self): + print ('idle_workers.value %d' % self._idle_worker_count()) + + + def _get_master_pid(self): + master_pid_file = open(GUNICORN_PID_PATH) + self.master_pid = master_pid_file.read().rstrip() + master_pid_file.close() + + def _get_worker_pids(self, master_pid): + children = check_output( + ['ps', '--ppid', master_pid, '-o', 'pid', '--no-headers']) + self.worker_pids = [pid.strip() for pid in children.splitlines()] + + def _worker_count(self): + return len(self.worker_pids) + + def _idle_worker_count(self): + idle_workers = 0 + for pid in self.worker_pids: + before = self._cpu_time(pid) + sleep(0.50) + after = self._cpu_time(pid) + if before == after: + idle_workers += 1 + return idle_workers + + def _cpu_time(self, pid): + proc_info = open('/proc/%s/stat' % pid).read() + proc_info = [field.rstrip() for field in proc_info.split()] + user_time = int(proc_info[13].rstrip()) + kernel_time = int(proc_info[14].rstrip()) + return user_time + kernel_time + +def print_config(): + print "graph_title Gunicorn - Status" + print "graph_args -l 0" + print "graph_vlabel Number of workers" + print "graph_category gunicorn" + print "total_workers.label Total Workers" + print "idle_workers.label Idle Workers" + +if __name__ == "__main__": + if len(sys.argv) == 2 and sys.argv[1] == 'config': + print_config() + elif len(sys.argv) == 2 and sys.argv[1] == 'autoconf': + try: + open(GUNICORN_PID_PATH).close() + print "yes" + except: + print "no" + # Some docs say it'll be called with fetch, some say no arg at all + elif len(sys.argv) == 1 or (len(sys.argv) == 2 and sys.argv[1] == 'fetch'): + status = GunicornStatus() + try: + status.print_total_workers() + status.print_idle_workers() + except: + sys.exit("Couldn't retrieve gunicorn status") diff --git a/plugins/other/hadoop-dfs-plugin b/plugins/hadoop/hadoop-dfs-plugin similarity index 100% rename from plugins/other/hadoop-dfs-plugin rename to plugins/hadoop/hadoop-dfs-plugin diff --git a/plugins/other/haproxy-bytes b/plugins/haproxy/haproxy-bytes similarity index 100% rename from plugins/other/haproxy-bytes rename to plugins/haproxy/haproxy-bytes diff --git a/plugins/other/haproxy-connection-errors b/plugins/haproxy/haproxy-connection-errors similarity index 100% rename from plugins/other/haproxy-connection-errors rename to plugins/haproxy/haproxy-connection-errors diff --git a/plugins/other/haproxy-downtime b/plugins/haproxy/haproxy-downtime similarity index 100% rename from plugins/other/haproxy-downtime rename to plugins/haproxy/haproxy-downtime diff --git a/plugins/other/haproxy-errors b/plugins/haproxy/haproxy-errors similarity index 100% rename from plugins/other/haproxy-errors rename to plugins/haproxy/haproxy-errors diff --git a/plugins/other/haproxy-failed-checks b/plugins/haproxy/haproxy-failed-checks similarity index 100% rename from plugins/other/haproxy-failed-checks rename to plugins/haproxy/haproxy-failed-checks diff --git a/plugins/other/haproxy-response-errors b/plugins/haproxy/haproxy-response-errors similarity index 100% rename from plugins/other/haproxy-response-errors rename to plugins/haproxy/haproxy-response-errors diff --git a/plugins/other/haproxy-sessions b/plugins/haproxy/haproxy-sessions similarity index 100% rename from plugins/other/haproxy-sessions rename to plugins/haproxy/haproxy-sessions diff --git a/plugins/other/haproxy-sessions-by-servers b/plugins/haproxy/haproxy-sessions-by-servers similarity index 100% rename from plugins/other/haproxy-sessions-by-servers rename to plugins/haproxy/haproxy-sessions-by-servers diff --git a/plugins/other/apc_status b/plugins/hardware/apc_status similarity index 100% rename from plugins/other/apc_status rename to plugins/hardware/apc_status diff --git a/plugins/other/healthcheck_log b/plugins/healthcheck/healthcheck_log similarity index 100% rename from plugins/other/healthcheck_log rename to plugins/healthcheck/healthcheck_log diff --git a/plugins/other/healthcheck_process b/plugins/healthcheck/healthcheck_process similarity index 100% rename from plugins/other/healthcheck_process rename to plugins/healthcheck/healthcheck_process diff --git a/plugins/other/healthcheck_url b/plugins/healthcheck/healthcheck_url similarity index 100% rename from plugins/other/healthcheck_url rename to plugins/healthcheck/healthcheck_url diff --git a/plugins/other/heimdal_kdc_bandwidth b/plugins/heimdal/heimdal_kdc_bandwidth similarity index 100% rename from plugins/other/heimdal_kdc_bandwidth rename to plugins/heimdal/heimdal_kdc_bandwidth diff --git a/plugins/other/heimdal_kdc_requests b/plugins/heimdal/heimdal_kdc_requests similarity index 100% rename from plugins/other/heimdal_kdc_requests rename to plugins/heimdal/heimdal_kdc_requests diff --git a/plugins/other/hp2600_count_ b/plugins/hp2600/hp2600_count_ similarity index 100% rename from plugins/other/hp2600_count_ rename to plugins/hp2600/hp2600_count_ diff --git a/plugins/other/hp2600_status_ b/plugins/hp2600/hp2600_status_ similarity index 100% rename from plugins/other/hp2600_status_ rename to plugins/hp2600/hp2600_status_ diff --git a/plugins/other/http_load_ b/plugins/http/http_load_ similarity index 100% rename from plugins/other/http_load_ rename to plugins/http/http_load_ diff --git a/plugins/other/http_request_time b/plugins/http/http_request_time similarity index 100% rename from plugins/other/http_request_time rename to plugins/http/http_request_time diff --git a/plugins/other/http_responsetime b/plugins/http/http_responsetime similarity index 100% rename from plugins/other/http_responsetime rename to plugins/http/http_responsetime diff --git a/plugins/other/multi_http_responsetime b/plugins/http/multi_http_responsetime similarity index 100% rename from plugins/other/multi_http_responsetime rename to plugins/http/multi_http_responsetime diff --git a/plugins/other/speedport_300 b/plugins/http/speedport_300 similarity index 100% rename from plugins/other/speedport_300 rename to plugins/http/speedport_300 diff --git a/plugins/other/wget_page b/plugins/http/wget_page similarity index 100% rename from plugins/other/wget_page rename to plugins/http/wget_page diff --git a/plugins/other/icecast2_ b/plugins/icecast/icecast2_ similarity index 100% rename from plugins/other/icecast2_ rename to plugins/icecast/icecast2_ diff --git a/plugins/other/icecast2_all b/plugins/icecast/icecast2_all similarity index 100% rename from plugins/other/icecast2_all rename to plugins/icecast/icecast2_all diff --git a/plugins/other/icecast2_simple b/plugins/icecast/icecast2_simple similarity index 100% rename from plugins/other/icecast2_simple rename to plugins/icecast/icecast2_simple diff --git a/plugins/other/icecast_ b/plugins/icecast/icecast_ similarity index 100% rename from plugins/other/icecast_ rename to plugins/icecast/icecast_ diff --git a/plugins/other/ddclient b/plugins/ip/ddclient similarity index 100% rename from plugins/other/ddclient rename to plugins/ip/ddclient diff --git a/plugins/other/ipmi_ b/plugins/ipmi/ipmi_ similarity index 100% rename from plugins/other/ipmi_ rename to plugins/ipmi/ipmi_ diff --git a/plugins/other/joomla-sessions b/plugins/joomla/joomla-sessions similarity index 100% rename from plugins/other/joomla-sessions rename to plugins/joomla/joomla-sessions diff --git a/plugins/other/jstat__gccount b/plugins/jvm/jstat__gccount similarity index 100% rename from plugins/other/jstat__gccount rename to plugins/jvm/jstat__gccount diff --git a/plugins/other/jstat__gctime b/plugins/jvm/jstat__gctime similarity index 100% rename from plugins/other/jstat__gctime rename to plugins/jvm/jstat__gctime diff --git a/plugins/other/jstat__heap b/plugins/jvm/jstat__heap similarity index 100% rename from plugins/other/jstat__heap rename to plugins/jvm/jstat__heap diff --git a/plugins/other/jvm_sun_memory b/plugins/jvm/jvm_sun_memory similarity index 100% rename from plugins/other/jvm_sun_memory rename to plugins/jvm/jvm_sun_memory diff --git a/plugins/other/jvm_sun_minorgcs b/plugins/jvm/jvm_sun_minorgcs similarity index 100% rename from plugins/other/jvm_sun_minorgcs rename to plugins/jvm/jvm_sun_minorgcs diff --git a/plugins/other/jvm_sun_tenuredgcs b/plugins/jvm/jvm_sun_tenuredgcs similarity index 100% rename from plugins/other/jvm_sun_tenuredgcs rename to plugins/jvm/jvm_sun_tenuredgcs diff --git a/plugins/other/kvm_cpu b/plugins/kvm/kvm_cpu similarity index 100% rename from plugins/other/kvm_cpu rename to plugins/kvm/kvm_cpu diff --git a/plugins/other/kvm_io b/plugins/kvm/kvm_io similarity index 100% rename from plugins/other/kvm_io rename to plugins/kvm/kvm_io diff --git a/plugins/other/kvm_mem b/plugins/kvm/kvm_mem similarity index 100% rename from plugins/other/kvm_mem rename to plugins/kvm/kvm_mem diff --git a/plugins/other/kvm_net b/plugins/kvm/kvm_net similarity index 100% rename from plugins/other/kvm_net rename to plugins/kvm/kvm_net diff --git a/plugins/other/munin-libvirtpy b/plugins/kvm/munin-libvirtpy similarity index 100% rename from plugins/other/munin-libvirtpy rename to plugins/kvm/munin-libvirtpy diff --git a/plugins/other/flexlm_ b/plugins/licensing/flexlm_ similarity index 100% rename from plugins/other/flexlm_ rename to plugins/licensing/flexlm_ diff --git a/plugins/other/logins b/plugins/logins/logins similarity index 100% rename from plugins/other/logins rename to plugins/logins/logins diff --git a/plugins/other/lustre_abs b/plugins/lustre/lustre_abs similarity index 100% rename from plugins/other/lustre_abs rename to plugins/lustre/lustre_abs diff --git a/plugins/other/lustre_df b/plugins/lustre/lustre_df similarity index 100% rename from plugins/other/lustre_df rename to plugins/lustre/lustre_df diff --git a/plugins/other/lustre_df_free b/plugins/lustre/lustre_df_free similarity index 100% rename from plugins/other/lustre_df_free rename to plugins/lustre/lustre_df_free diff --git a/plugins/other/lustre_df_indodes b/plugins/lustre/lustre_df_indodes similarity index 100% rename from plugins/other/lustre_df_indodes rename to plugins/lustre/lustre_df_indodes diff --git a/plugins/other/amavis_ b/plugins/mail/amavis_ similarity index 100% rename from plugins/other/amavis_ rename to plugins/mail/amavis_ diff --git a/plugins/other/amavis_awk b/plugins/mail/amavis_awk similarity index 100% rename from plugins/other/amavis_awk rename to plugins/mail/amavis_awk diff --git a/plugins/other/clamav b/plugins/mail/clamav similarity index 100% rename from plugins/other/clamav rename to plugins/mail/clamav diff --git a/plugins/other/courier_log b/plugins/mail/courier_log similarity index 100% rename from plugins/other/courier_log rename to plugins/mail/courier_log diff --git a/plugins/other/dkimproxy_mails b/plugins/mail/dkimproxy_mails similarity index 100% rename from plugins/other/dkimproxy_mails rename to plugins/mail/dkimproxy_mails diff --git a/plugins/other/mail_connections b/plugins/mail/mail_connections similarity index 100% rename from plugins/other/mail_connections rename to plugins/mail/mail_connections diff --git a/plugins/other/mixminion b/plugins/mail/mixminion similarity index 100% rename from plugins/other/mixminion rename to plugins/mail/mixminion diff --git a/plugins/other/postfix-policyd b/plugins/mail/postfix-policyd similarity index 100% rename from plugins/other/postfix-policyd rename to plugins/mail/postfix-policyd diff --git a/plugins/other/postfix-rbl-blocked-mails b/plugins/mail/postfix-rbl-blocked-mails similarity index 100% rename from plugins/other/postfix-rbl-blocked-mails rename to plugins/mail/postfix-rbl-blocked-mails diff --git a/plugins/other/postfix_filtered b/plugins/mail/postfix_filtered similarity index 100% rename from plugins/other/postfix_filtered rename to plugins/mail/postfix_filtered diff --git a/plugins/other/postfix_filtered_awk b/plugins/mail/postfix_filtered_awk similarity index 100% rename from plugins/other/postfix_filtered_awk rename to plugins/mail/postfix_filtered_awk diff --git a/plugins/other/postfix_mailfiltered b/plugins/mail/postfix_mailfiltered similarity index 100% rename from plugins/other/postfix_mailfiltered rename to plugins/mail/postfix_mailfiltered diff --git a/plugins/other/postfix_stats b/plugins/mail/postfix_stats similarity index 100% rename from plugins/other/postfix_stats rename to plugins/mail/postfix_stats diff --git a/plugins/other/postgrey b/plugins/mail/postgrey similarity index 100% rename from plugins/other/postgrey rename to plugins/mail/postgrey diff --git a/plugins/other/postgrey-new b/plugins/mail/postgrey-new similarity index 100% rename from plugins/other/postgrey-new rename to plugins/mail/postgrey-new diff --git a/plugins/other/procmail_ b/plugins/mail/procmail_ similarity index 100% rename from plugins/other/procmail_ rename to plugins/mail/procmail_ diff --git a/plugins/other/qmailconn b/plugins/mail/qmailconn similarity index 100% rename from plugins/other/qmailconn rename to plugins/mail/qmailconn diff --git a/plugins/other/qmailsend b/plugins/mail/qmailsend similarity index 100% rename from plugins/other/qmailsend rename to plugins/mail/qmailsend diff --git a/plugins/other/qmailsend_plesk b/plugins/mail/qmailsend_plesk similarity index 100% rename from plugins/other/qmailsend_plesk rename to plugins/mail/qmailsend_plesk diff --git a/plugins/other/qremote b/plugins/mail/qremote similarity index 100% rename from plugins/other/qremote rename to plugins/mail/qremote diff --git a/plugins/other/queuestats b/plugins/mail/queuestats similarity index 100% rename from plugins/other/queuestats rename to plugins/mail/queuestats diff --git a/plugins/other/sa-learn b/plugins/mail/sa-learn similarity index 100% rename from plugins/other/sa-learn rename to plugins/mail/sa-learn diff --git a/plugins/other/spamd-blacklist-bsd b/plugins/mail/spamd-blacklist-bsd similarity index 100% rename from plugins/other/spamd-blacklist-bsd rename to plugins/mail/spamd-blacklist-bsd diff --git a/plugins/other/spamd-tarpit-bsd b/plugins/mail/spamd-tarpit-bsd similarity index 100% rename from plugins/other/spamd-tarpit-bsd rename to plugins/mail/spamd-tarpit-bsd diff --git a/plugins/other/spamdyke b/plugins/mail/spamdyke similarity index 100% rename from plugins/other/spamdyke rename to plugins/mail/spamdyke diff --git a/plugins/other/eoc_subscribers_count b/plugins/mailinglist/eoc_subscribers_count similarity index 100% rename from plugins/other/eoc_subscribers_count rename to plugins/mailinglist/eoc_subscribers_count diff --git a/plugins/other/mailman_subscribers b/plugins/mailman/mailman_subscribers similarity index 100% rename from plugins/other/mailman_subscribers rename to plugins/mailman/mailman_subscribers diff --git a/plugins/other/memcached-multigraph-plugin b/plugins/memcached/memcached-multigraph-plugin similarity index 100% rename from plugins/other/memcached-multigraph-plugin rename to plugins/memcached/memcached-multigraph-plugin diff --git a/plugins/other/memcached_bytes_ b/plugins/memcached/memcached_bytes_ similarity index 100% rename from plugins/other/memcached_bytes_ rename to plugins/memcached/memcached_bytes_ diff --git a/plugins/other/memcached_bytes_all b/plugins/memcached/memcached_bytes_all similarity index 100% rename from plugins/other/memcached_bytes_all rename to plugins/memcached/memcached_bytes_all diff --git a/plugins/other/memcached_connections_ b/plugins/memcached/memcached_connections_ similarity index 100% rename from plugins/other/memcached_connections_ rename to plugins/memcached/memcached_connections_ diff --git a/plugins/other/memcached_hits_ b/plugins/memcached/memcached_hits_ similarity index 90% rename from plugins/other/memcached_hits_ rename to plugins/memcached/memcached_hits_ index 1c2982f6..d6697728 100755 --- a/plugins/other/memcached_hits_ +++ b/plugins/memcached/memcached_hits_ @@ -6,9 +6,16 @@ use warnings; use Cache::Memcached; +$0 =~ /memcached_hits_(\d+_\d+_\d+_\d+)_(\d+)$/; +my ($ip, $port) = ($1, $2); +$ip =~ s/_/./g; +my $address = "$ip:$port"; + +my $title = $ENV{title} || $address; + my $cmd = shift || ''; if ($cmd eq 'config') { - print "graph_title Memcached cache hits and misses\n"; + print "graph_title Memcached cache hits and misses -- $title\n"; print "graph_args --base 1000 -l 0\n"; print "graph_vlabel requests\n"; print "graph_category memcached\n"; @@ -25,11 +32,6 @@ if ($cmd eq 'config') { exit 0; } -$0 =~ /memcached_hits_(\d+_\d+_\d+_\d+)_(\d+)$/; -my ($ip, $port) = ($1, $2); -$ip =~ s/_/./g; -my $address = "$ip:$port"; - my $memd = new Cache::Memcached { 'servers' => [$address] }; my $memstats = $memd->stats(['misc']); diff --git a/plugins/other/memcached_items_ b/plugins/memcached/memcached_items_ similarity index 100% rename from plugins/other/memcached_items_ rename to plugins/memcached/memcached_items_ diff --git a/plugins/other/memcached-multigraph b/plugins/memcached/memcached_multi_ similarity index 67% rename from plugins/other/memcached-multigraph rename to plugins/memcached/memcached_multi_ index eac6a90c..e574861f 100755 --- a/plugins/other/memcached-multigraph +++ b/plugins/memcached/memcached_multi_ @@ -1,6 +1,6 @@ #!/usr/bin/perl # -=head1 NAME +=head1 MEMCACHED Memcached - A Plugin to monitor Memcached Servers (Multigraph) @@ -36,9 +36,6 @@ items => I This graphs the current items and total items in the memc memory => I This graphs the current and max memory allocation B -The following example holds true for all graphing options in this plugin. - Example: ln -s /usr/share/munin/plugins/memcached_multi_ /etc/munin/plugins/memcached_multi_bytes - =head1 ADDITIONAL INFORMATION You will find that some of the graphs have LEI on them. This was done in order to save room @@ -52,13 +49,11 @@ The B variable formats certain graphs based on the following guidelin =head1 ACKNOWLEDGEMENTS -The core of this plugin is based on the mysql_ plugin maintained by Kjell-Magne Ãierud - -Thanks to dormando as well for putting up with me ;) +Thanks to dormando for putting up with me ;) =head1 AUTHOR -Matt West < https://code.google.com/p/memcached-munin-plugin/ > +Matt West < https://github.com/mhwest13/Memcached-Munin-Plugin > =head1 LICENSE @@ -72,54 +67,77 @@ GPLv2 =cut use strict; +use warnings; use IO::Socket; use Munin::Plugin; +use File::Basename; +if (basename($0) !~ /^memcached_multi_/) { + print "This script needs to be named memcached_multi_ and have symlinks which start the same.\n"; + exit 1; +} + +# tell munin about our multigraph capabilities need_multigraph(); +=head1 Variable Declarations + + This section of code is to declare the variables used throughout the plugin + Some of them are imported as environment variables from munin plugin conf.d + file, others are hashes used for storing information that comes from the + stats commands issued to memcached. + +=cut + +# lets import environment variables for the plugin or use the default my $host = $ENV{host} || "127.0.0.1"; my $port = $ENV{port} || 11211; -my %stats; -# This hash contains the information contained in two memcache commands -# stats and stats settings. - -my %items; -# This gives us eviction rates and other hit stats per slab -# We track this so we can see if something was evicted earlier than necessary - -my %chnks; -# This gives us the memory size and usage per slab -# We track this so we can see what slab is being used the most and has no free chunks -# so we can re-tune memcached to allocate more pages for the specified chunk size - -my $timescale = $ENV{timescale} || 3; # This gives us the ability to control the timescale our graphs are displaying. # The default it set to divide by hours, if you want to get seconds set it to 1. # Options: 1 = seconds, 2 = minutes, 3 = hours, 4 = days +my $timescale = $ENV{timescale} || 3; + +# This hash contains the information contained in two memcache commands +# stats and stats settings. +my %stats; + +# This gives us eviction rates and other hit stats per slab +# We track this so we can see if something was evicted earlier than necessary +my %items; + +# This gives us the memory size and usage per slab +# We track this so we can see what slab is being used the most and has no free chunks +# so we can re-tune memcached to allocate more pages for the specified chunk size +my %chnks; + +=head2 Graph Declarations + + This block of code builds up all of the graph info for all root / sub graphs. + + %graphs: is a container for all of the graph definition information. In here is where you'll + find the configuration information for munin's graphing procedure. + Format: + + $graph{graph_name} => { + config => { + You'll find the main graph config stored here + { key => value }, + { ... }, + }, + datasrc => [ + Name: name given to data value + Attr: Attribute and value, attribute must be valid plugin argument + { name => 'Name', info => 'info about graph', ... }, + { ... }, + ], + } + +=cut -# So I was trying to figure out how to build this up, and looking at some good examples -# I decided to use the format, or for the most part, the format from the mysql_ munin plugin -# for Innodb by Kjell-Magne Ãierud, it just spoke ease of flexibility especially with multigraphs -# thanks btw ;) -# -# %graphs is a container for all of the graph definition information. In here is where you'll -# find the configuration information for munin's graphing procedure. -# Format: -# -# $graph{graph_name} => { -# config => { -# # You'll find keys and values stored here for graph manipulation -# }, -# datasrc => [ -# # Name: name given to data value -# # Attr: Attribute for given value -# { name => 'Name', (Attr) }, -# { ... }, -# ], -# } my %graphs; +# main graph for memcached item count $graphs{items} = { config => { args => '--base 1000 --lower-limit 0', @@ -133,7 +151,7 @@ $graphs{items} = { { name => 'total_items', label => 'New Items', min => '0', type => 'DERIVE' }, ], }; - +# main graph for memcached memory usage $graphs{memory} = { config => { args => '--base 1024 --lower-limit 0', @@ -147,7 +165,7 @@ $graphs{memory} = { { name => 'bytes', draw => 'AREA', label => 'Current Bytes Used', min => '0' }, ], }; - +# main graph for memcached network usage $graphs{bytes} = { config => { args => '--base 1000', @@ -162,7 +180,7 @@ $graphs{bytes} = { { name => 'bytes_written', type => 'DERIVE', label => 'Traffic in (-) / out (+)', negative => 'bytes_read', cdef => 'bytes_written,8,*', min => '0' }, ], }; - +# graph for memcached connections $graphs{conns} = { config => { args => '--base 1000 --lower-limit 0', @@ -178,7 +196,7 @@ $graphs{conns} = { { name => 'avg_conns' , label => 'Avg Connections', min => '0' }, ], }; - +# main graph for memcached commands issued $graphs{commands} = { config => { args => '--base 1000 --lower-limit 0', @@ -200,7 +218,7 @@ $graphs{commands} = { { name => 'decr_misses', type => 'DERIVE', label => 'Decrement Misses', info => 'Number of unsuccessful decrement requests', min => '0' }, ], }; - +# main graph for memcached eviction rates $graphs{evictions} = { config => { args => '--base 1000 --lower-limit 0', @@ -215,7 +233,7 @@ $graphs{evictions} = { { name => 'reclaimed', label => 'Reclaimed Items', info => 'Cumulative Reclaimed Item Entries Across All Slabs', type => 'DERIVE', min => '0' }, ], }; - +# sub graph for breaking memory info down by slab ( sub graph of memory ) $graphs{slabchnks} = { config => { args => '--base 1000 --lower-limit 0', @@ -230,7 +248,7 @@ $graphs{slabchnks} = { { name => 'free_chunks', label => 'Total Chunks Not in Use (Free)', min => '0' }, ], }; - +# sub graph for breaking commands down by slab ( sub graph of commands ) $graphs{slabhits} = { config => { args => '--base 1000 --lower-limit 0', @@ -247,7 +265,7 @@ $graphs{slabhits} = { { name => 'decr_hits', label => 'Decrement Requests', type => 'DERIVE', min => '0' }, ], }; - +# sub graph for breaking evictions down by slab ( sub graph of evictions ) $graphs{slabevics} = { config => { args => '--base 1000 --lower-limit 0', @@ -262,7 +280,7 @@ $graphs{slabevics} = { { name => 'reclaimed', label => 'Reclaimed Expired Items', info => 'This is number of times items were stored in expired entry memory space', type => 'DERIVE', min => '0' }, ], }; - +# sub graph for showing the time between an item was last evicted and requested ( sub graph of evictions ) $graphs{slabevictime} = { config => { args => '--base 1000 --lower-limit 0', @@ -275,7 +293,7 @@ $graphs{slabevictime} = { { name => 'evicted_time', label => 'Eviction Time (LEI)', info => 'Time Since Request for Last Evicted Item', min => '0' }, ], }; - +# sub graph for breaking items down by slab ( sub graph of items ) $graphs{slabitems} = { config => { args => '--base 1000 --lower-limit 0', @@ -288,7 +306,7 @@ $graphs{slabitems} = { { name => 'number', label => 'Items', info => 'This is the amount of items stored in this slab', min => '0' }, ], }; - +# sub graph for showing the age of the eldest item stored in a slab ( sub graph of items ) $graphs{slabitemtime} = { config => { args => '--base 1000 --lower-limit 0', @@ -302,37 +320,47 @@ $graphs{slabitemtime} = { ], }; -## -#### Config Check #### -## +=head1 Munin Checks + + These checks look for config / autoconf / suggest params + +=head2 Config Check + + This block of code looks at the argument that is possibly supplied, + should it be config, it then checks to make sure the plugin + specified exists, assuming it does, it will run the do_config + subroutine for the plugin specified, otherwise it dies complaining + about an unknown plugin. + +=cut if (defined $ARGV[0] && $ARGV[0] eq 'config') { - + # Lets get our plugin from the symlink being called up, we'll also verify its a valid + # plugin that we have graph information for $0 =~ /memcached_multi_(.+)*/; my $plugin = $1; - die 'Unknown Plugin Specified: ' . ($plugin ? $plugin : '') unless $graphs{$plugin}; - # We need to fetch the stats before we do any config, cause its needed for multigraph + # subgraphs which use slab information for title / info per slab fetch_stats(); - # Now lets go ahead and print out our config. do_config($plugin); exit 0; } -## -#### Autoconf Check #### -## +=head2 Autoconf Check + + This block of code looks at the argument that is possibly supplied, + should it be autoconf, we will attempt to connect to the memcached + service specified on the host:port, upon successful connection it + prints yes, otherwise it prints no. + +=cut if (defined $ARGV[0] && $ARGV[0] eq 'autoconf') { - - my $s = IO::Socket::INET->new( - Proto => "tcp", - PeerAddr => $host, - PeerPort => $port, - ); - + # Lets attempt to connect to memcached + my $s = get_conn(); + # Lets verify that we did connect to memcached if (defined($s)) { print "yes\n"; exit 0; @@ -342,18 +370,21 @@ if (defined $ARGV[0] && $ARGV[0] eq 'autoconf') { } } -## -#### Suggest Check #### -## +=head2 Suggest Check + + This block of code looks at the argument that is possibly supplied, + should it be suggest, we are going to print the possible plugins + which can be specified. Note we only specify the root graphs for the + multigraphs, since the rest of the subgraphs will appear "behind" the + root graphs. It also attempts to connect to the memcached service to + verify it is infact running. + +=cut if (defined $ARGV[0] && $ARGV[0] eq 'suggest') { - - my $s = IO::Socket::INET->new( - Proto => "tcp", - PeerAddr => $host, - PeerPort => $port, - ); - + # Lets attempt to connect to memcached + my $s = get_conn(); + # Lets check that we did connect to memcached if (defined($s)) { my @rootplugins = ('bytes','conns','commands','evictions','items','memory'); foreach my $plugin (@rootplugins) { @@ -366,30 +397,29 @@ if (defined $ARGV[0] && $ARGV[0] eq 'suggest') { } } -## -#### Well We aren't running (auto)config/suggest so lets print some stats #### -## +=head1 Output Subroutines + Output Subroutine calls to output data values + +=head2 fetch_output + + This subroutine is the main call for printing data for the plugin. + No parameters are taken as this is the default call if no arguments + are supplied from the command line. + +=cut + +# Well, no arguments were supplied that we know about, so lets print some data fetch_output(); -## -#### Subroutines for printing info gathered from memcached #### -## - -## -#### This subroutine performs the bulk processing for printing statistics. -## - sub fetch_output { - + # Lets get our plugin from the symlink being called up, we'll also verify its a valid + # plugin that we have graph information for $0 =~ /memcached_multi_(.+)*/; my $plugin = $1; - die 'Unknown Plugin Specified: ' . ($plugin ? $plugin : '') unless $graphs{$plugin}; - # Well we need to actually fetch the stats before we do anything to them. fetch_stats(); - # Now lets go ahead and print out our output. my @subgraphs; if ($plugin eq 'memory') { @@ -423,17 +453,24 @@ sub fetch_output { return; } -## -#### This subroutine is for the root non-multigraph graphs which render on the main node page #### -## +=head2 print_root_output + + This block of code prints out the return values for our root graphs. It takes + one parameter $plugin. Returns when completed, this is the non multigraph + output subroutine. + + $plugin; graph we are calling up to print data values for + + Example: print_root_output($plugin); + +=cut sub print_root_output { + # Lets get our plugin, set our graph reference and print out info for Munin my ($plugin) = (@_); - my $graph = $graphs{$plugin}; - print "graph memcached_$plugin\n"; - + # The conns plugin has some specific needs, looking for plugin type if ($plugin ne 'conns') { foreach my $dsrc (@{$graph->{datasrc}}) { my %datasrc = %$dsrc; @@ -461,26 +498,33 @@ sub print_root_output { } } } - return; } -## -#### This subroutine is for the root multigraph graphs which render on the main node page #### -## +=head2 print_rootmulti_output + + This block of code prints out the return values for our root graphs. It takes + one parameter $plugin. Returns when completed, this is the multigraph + output subroutine + + $plugin; main(root) graph we are calling up to print data values for + + Example: print_rootmulti_output($plugin); + +=cut sub print_rootmulti_output { + # Lets get our plugin, set our graph reference and print out info for Munin my ($plugin) = (@_); - my $graph = $graphs{$plugin}; - print "multigraph memcached_$plugin\n"; - + # Lets print our data values with their appropriate name foreach my $dsrc (@{$graph->{datasrc}}) { my $output = 0; my %datasrc = %$dsrc; while ( my ($key, $value) = each(%datasrc)) { next if ($key ne 'name'); + next if (($plugin eq 'evictions') && ($value eq 'reclaimed') && ($stats{version} =~ /1\.4\.[0-2]/)); if (($plugin eq 'evictions') && ($value eq 'evicted_nonzero')) { foreach my $slabid (sort{$a <=> $b} keys %items) { $output += $items{$slabid}->{evicted_nonzero}; @@ -491,24 +535,33 @@ sub print_rootmulti_output { print "$dsrc->{name}.value $output\n"; } } - return; } -## -#### This subroutine is for the sub multigraph graphs created via the multigraph plugin #### -## +=head2 print_submulti_output + + This block of code prints out the return values for our root graphs. It takes + three parameters $slabid, $plugin and @subgraphs. Returns when completed, this + is the multigraph output subroutine for our subgraphs + + $slabid; slab id that we will use to grab info from and print out + $plugin; main(root) being called, used for multigraph output and slab id + @subgraphs; graphs we are actually trying to print data values for + + Example: print_submulti_output($slabid,$plugin,@subgraphs); + +=cut sub print_submulti_output { + # Lets get our slabid, plugin, and subgraphs my ($slabid,$plugin,@subgraphs) = (@_); my $currslab = undef; - + # Time to loop over our subgraphs array foreach my $sgraph (@subgraphs) { - + # Lets set our graph reference for quick calling, and print some info for munin my $graph = $graphs{$sgraph}; - print "multigraph memcached_$plugin.$sgraph\_$slabid\n"; - + # Lets figure out what slab info we are trying to call up if ($plugin eq 'evictions') { $currslab = $items{$slabid}; } elsif ($plugin eq 'memory') { @@ -520,11 +573,12 @@ sub print_submulti_output { } else { return; } - + # Lets print our data values with their appropriate name foreach my $dsrc (@{$graph->{datasrc}}) { my %datasrc = %$dsrc; while ( my ($key, $value) = each(%datasrc)) { next if ($key ne 'name'); + next if (($sgraph eq 'slabevics') && ($value eq 'reclaimed') && ($stats{version} =~ /1\.4\.[0-2]/)); my $output = $currslab->{$value}; if (($sgraph eq 'slabevictime') || ($sgraph eq 'slabitemtime')) { $output = time_scale('data',$output); ; @@ -533,17 +587,23 @@ sub print_submulti_output { } } } - return; } -## -#### Subroutines for printing out config information for graphs #### -## +=head1 Config Subroutines -## -#### This subroutine does the bulk printing the config info per graph #### -## + These subroutines handle the config portion of munin calls. + +=head2 do_config + + This is the main call issued assuming we call up config and plugin specified exists + The subroutine takes one parameter $plugin, and returns when completed. + + $plugin; main(root) graph being called + + Example: do_config($plugin); + +=cut sub do_config { my ($plugin) = (@_); @@ -579,22 +639,59 @@ sub do_config { return; } -## -#### This subroutine is for the config info for sub multigraph graphs created via the multigraph plugin #### -## +=head2 get_conn + + This subroutine returns a socket connection + +=cut + +sub get_conn { + my $s = undef; + + # check if we want to use sockets instead of tcp + my ($sock) = ($host =~ /unix:\/\/(.+)*$/); + + if ($sock) { + $s = IO::Socket::UNIX->new( + Peer => $sock + ); + } else { + $s = IO::Socket::INET->new( + Proto => "tcp", + PeerAddr => $host, + PeerPort => $port, + Timeout => 10, + ); + } + + return $s; +} + +=head2 print_submulti_config + + This subroutine prints out the config information for all of the subgraphs. + It takes three parameters, $slabid, $plugin and @subgraphs, returns when + completed, this is the mutligraph config output for our subgraphs + + $slabid; slab id that we will use to grab info from and print out + $plugin; main(root) being called, used for multigraph output and slab id + @subgraphs; graphs we are actually trying to print data values for + + Example: print_submulti_config($slabid,$plugin,@subgraphs); + +=cut sub print_submulti_config { + # Lets get our slabid, plugin, and subgraphs my ($slabid,$plugin,@subgraphs) = (@_); my ($slabitems,$slabchnks) = undef; - + # Time to loop over our subgraphs array foreach my $sgraph (@subgraphs) { - + # Lets set our graph reference, and main graph config for easy handling my $graph = $graphs{$sgraph}; - my %graphconf = %{$graph->{config}}; - + # Lets tell munin which graph we are graphing, and what our main graph config info is print "multigraph memcached_$plugin.$sgraph\_$slabid\n"; - while ( my ($key, $value) = each(%graphconf)) { if ($key eq 'title') { print "graph_$key $value" . "$slabid" . " ($chnks{$slabid}->{chunk_size} Bytes)\n"; @@ -605,7 +702,7 @@ sub print_submulti_config { print "graph_$key $value\n"; } } - + # Lets tell munin about our data values and how to treat them foreach my $dsrc (@{$graph->{datasrc}}) { my %datasrc = %$dsrc; while ( my ($key, $value) = each(%datasrc)) { @@ -618,25 +715,28 @@ sub print_submulti_config { return; } -## -#### This subroutine is for the config info for root multigraph graphs which render on the main node page #### -## +=head2 print_rootmulti_config + + This subroutine prints out the config information for all of the main(root) graphs. + It takes one parameter, $plugin, returns when completed. + + $plugin; main(root) graph used for multigraph call + + Example: print_rootmulti_config($plugin); + +=cut sub print_rootmulti_config { + # Lets get out plugin, set our graph reference and our graph config info my ($plugin) = (@_); - - die 'Unknown Plugin Specified: ' . ($plugin ? $plugin : '') unless $graphs{$plugin}; - my $graph = $graphs{$plugin}; - my %graphconf = %{$graph->{config}}; - + # Lets tell munin about the graph we are referencing and print the main config print "multigraph memcached_$plugin\n"; - while ( my ($key, $value) = each(%graphconf)) { print "graph_$key $value\n"; } - + # Lets tell munin about our data values and how to treat them foreach my $dsrc (@{$graph->{datasrc}}) { my %datasrc = %$dsrc; while ( my ($key, $value) = each(%datasrc)) { @@ -644,29 +744,31 @@ sub print_rootmulti_config { print "$dsrc->{name}.$key $value\n"; } } - return; } -## -#### This subroutine is for the config info for non multigraph graphs which render on the main node page #### -## +=head2 print_root_config + + This subroutine prints out the config information for all of the main(root) graphs. + It takes one parameter, $plugin, returns when completed. + + $plugin; main(root) graph used for multigraph call + + Example: print_root_config($plugin); + +=cut sub print_root_config { + # Lets get our plugin, set our graph reference and our graph config info my ($plugin) = (@_); - - die 'Unknown Plugin Specified: ' . ($plugin ? $plugin : '') unless $graphs{$plugin}; - my $graph = $graphs{$plugin}; - my %graphconf = %{$graph->{config}}; - + # Lets tell munin about the graph we are referencing and print the main config print "graph memcached_$plugin\n"; - while ( my ($key, $value) = each(%graphconf)) { print "graph_$key $value\n"; } - + # Lets tell munin about our data values and how to treat them foreach my $dsrc (@{$graph->{datasrc}}) { my %datasrc = %$dsrc; while ( my ($key, $value) = each(%datasrc)) { @@ -674,46 +776,46 @@ sub print_root_config { print "$dsrc->{name}.$key $value\n"; } } - return; } -## -#### This subroutine actually performs the data fetch for us #### -#### These commands do not lock up Memcache at all #### -## +=head1 Misc Subroutines + + These subroutines are misc ones, and are referenced inside of the code. They + should never be called up by Munin. + +=head2 fetch_stats + + This subroutine fetches the information from memcached and stores it into our + hashes for later referencing throughout the graph. Returns when completed + +=cut sub fetch_stats { - my $s = IO::Socket::INET->new( - Proto => "tcp", - PeerAddr => $host, - PeerPort => $port, - ); - + # Lets try and connect to memcached + my $s = get_conn(); + # Die if we can't establish a connection to memcached die "Error: Unable to Connect to $host\[:$port\]\n" unless $s; - + # Lets print the stats command and store the info from the output print $s "stats\r\n"; - while (my $line = <$s>) { - if ($line =~ /STAT\s(.+?)\s(\d+)/) { + if ($line =~ /STAT\s(.+?)\s(.*)/) { my ($skey,$svalue) = ($1,$2); $stats{$skey} = $svalue; } last if $line =~ /^END/; } - + # Lets print the stats settings command and store the info from the output print $s "stats settings\r\n"; - while (my $line = <$s>) { - if ($line =~ /STAT\s(.+?)\s(\d+)/) { + if ($line =~ /STAT\s(.+?)\s(.*)/) { my ($skey,$svalue) = ($1,$2); $stats{$skey} = $svalue; } last if $line =~ /^END/; } - + # Lets print the stats slabs command and store the info from the output print $s "stats slabs\r\n"; - while (my $line = <$s>) { if ($line =~ /STAT\s(\d+):(.+)\s(\d+)/) { my ($slabid,$slabkey,$slabvalue) = ($1,$2,$3); @@ -721,9 +823,8 @@ sub fetch_stats { } last if $line =~ /^END/; } - + # Lets print the stats items command and store the info from the output print $s "stats items\r\n"; - while (my $line = <$s>) { if ($line =~ /STAT\sitems:(\d+):(.+?)\s(\d+)/) { my ($itemid,$itemkey,$itemvalue) = ($1,$2,$3); @@ -733,14 +834,23 @@ sub fetch_stats { } } -## -#### This subroutine is to help manage the time_scale settings for the graph -## +=head2 time_scale + + This subroutine is here for me to adjust the timescale of the time graphs + for last evicted item and age of eldest item in cache. + + Please note, after long usage I have noticed these counters may not + be accurate, I believe the developers are aware and have submitted + a patch upstream. + +=cut sub time_scale { + # Lets get our config option and value to adjust my ($configopt,$origvalue) = (@_); my $value; - + # If config is defined, it returns the config info for time scale + # If data is defined, it returns the original value after its been adjusted if ($configopt eq 'config') { if ($timescale == 1) { $value = "Seconds" . $origvalue; diff --git a/plugins/other/memcached_requests_ b/plugins/memcached/memcached_requests_ similarity index 91% rename from plugins/other/memcached_requests_ rename to plugins/memcached/memcached_requests_ index 284617fd..b414b674 100755 --- a/plugins/other/memcached_requests_ +++ b/plugins/memcached/memcached_requests_ @@ -6,9 +6,16 @@ use warnings; use Cache::Memcached; +$0 =~ /memcached_requests_(\d+_\d+_\d+_\d+)_(\d+)$/; +my ($ip, $port) = ($1, $2); +$ip =~ s/_/./g; +my $address = "$ip:$port"; + +my $title = $ENV{title} || $address; + my $cmd = shift || ''; if ($cmd eq 'config') { - print "graph_title Memcached requests\n"; + print "graph_title Memcached requests -- $title\n"; print "graph_args --base 1000 -l 0\n"; print "graph_vlabel requests\n"; print "graph_category memcached\n"; @@ -26,11 +33,6 @@ if ($cmd eq 'config') { exit 0; } -$0 =~ /memcached_requests_(\d+_\d+_\d+_\d+)_(\d+)$/; -my ($ip, $port) = ($1, $2); -$ip =~ s/_/./g; -my $address = "$ip:$port"; - my $memd = new Cache::Memcached { 'servers' => [$address] }; my $memstats = $memd->stats(['misc']); diff --git a/plugins/other/memcached_traffic_ b/plugins/memcached/memcached_traffic_ similarity index 100% rename from plugins/other/memcached_traffic_ rename to plugins/memcached/memcached_traffic_ diff --git a/plugins/other/mongrel_memory b/plugins/memory/mongrel_memory similarity index 100% rename from plugins/other/mongrel_memory rename to plugins/memory/mongrel_memory diff --git a/plugins/other/mongrel_process_memory b/plugins/memory/mongrel_process_memory similarity index 100% rename from plugins/other/mongrel_process_memory rename to plugins/memory/mongrel_process_memory diff --git a/plugins/other/minecraft-users b/plugins/minecraft/minecraft-users similarity index 100% rename from plugins/other/minecraft-users rename to plugins/minecraft/minecraft-users diff --git a/plugins/other/moblock_connections b/plugins/moblock/moblock_connections similarity index 100% rename from plugins/other/moblock_connections rename to plugins/moblock/moblock_connections diff --git a/plugins/other/mod_jk b/plugins/mod_jk/mod_jk similarity index 100% rename from plugins/other/mod_jk rename to plugins/mod_jk/mod_jk diff --git a/plugins/other/mogilefsd_activity b/plugins/mogilefs/mogilefsd_activity similarity index 100% rename from plugins/other/mogilefsd_activity rename to plugins/mogilefs/mogilefsd_activity diff --git a/plugins/other/mogilefsd_queries b/plugins/mogilefs/mogilefsd_queries similarity index 100% rename from plugins/other/mogilefsd_queries rename to plugins/mogilefs/mogilefsd_queries diff --git a/plugins/other/mongo_btree b/plugins/mongodb/mongo_btree similarity index 100% rename from plugins/other/mongo_btree rename to plugins/mongodb/mongo_btree diff --git a/plugins/other/mongo_conn b/plugins/mongodb/mongo_conn similarity index 100% rename from plugins/other/mongo_conn rename to plugins/mongodb/mongo_conn diff --git a/plugins/other/mongo_lock b/plugins/mongodb/mongo_lock similarity index 100% rename from plugins/other/mongo_lock rename to plugins/mongodb/mongo_lock diff --git a/plugins/other/mongo_mem b/plugins/mongodb/mongo_mem similarity index 100% rename from plugins/other/mongo_mem rename to plugins/mongodb/mongo_mem diff --git a/plugins/other/mongo_ops b/plugins/mongodb/mongo_ops similarity index 100% rename from plugins/other/mongo_ops rename to plugins/mongodb/mongo_ops diff --git a/plugins/other/monit_parser b/plugins/monit/monit_parser similarity index 100% rename from plugins/other/monit_parser rename to plugins/monit/monit_parser diff --git a/plugins/other/microsoft-sql b/plugins/mssql/microsoft-sql similarity index 100% rename from plugins/other/microsoft-sql rename to plugins/mssql/microsoft-sql diff --git a/plugins/other/microsoft-sql-buffer-cache-hit-ratio b/plugins/mssql/microsoft-sql-buffer-cache-hit-ratio similarity index 100% rename from plugins/other/microsoft-sql-buffer-cache-hit-ratio rename to plugins/mssql/microsoft-sql-buffer-cache-hit-ratio diff --git a/plugins/other/microsoft-sql-data-file-sizes b/plugins/mssql/microsoft-sql-data-file-sizes similarity index 100% rename from plugins/other/microsoft-sql-data-file-sizes rename to plugins/mssql/microsoft-sql-data-file-sizes diff --git a/plugins/other/microsoft-sql-log-file-size b/plugins/mssql/microsoft-sql-log-file-size similarity index 100% rename from plugins/other/microsoft-sql-log-file-size rename to plugins/mssql/microsoft-sql-log-file-size diff --git a/plugins/other/munin_stats_plugins b/plugins/munin/munin_stats_plugins similarity index 100% rename from plugins/other/munin_stats_plugins rename to plugins/munin/munin_stats_plugins diff --git a/plugins/other/mysql_connections b/plugins/mysql/mysql_connections similarity index 100% rename from plugins/other/mysql_connections rename to plugins/mysql/mysql_connections diff --git a/plugins/other/mysql_innodb b/plugins/mysql/mysql_innodb similarity index 100% rename from plugins/other/mysql_innodb rename to plugins/mysql/mysql_innodb diff --git a/plugins/other/mysql_qcache b/plugins/mysql/mysql_qcache similarity index 100% rename from plugins/other/mysql_qcache rename to plugins/mysql/mysql_qcache diff --git a/plugins/other/mysql_qcache_mem b/plugins/mysql/mysql_qcache_mem similarity index 100% rename from plugins/other/mysql_qcache_mem rename to plugins/mysql/mysql_qcache_mem diff --git a/plugins/other/mysql_report b/plugins/mysql/mysql_report similarity index 100% rename from plugins/other/mysql_report rename to plugins/mysql/mysql_report diff --git a/plugins/other/mysql_size_ b/plugins/mysql/mysql_size_ similarity index 100% rename from plugins/other/mysql_size_ rename to plugins/mysql/mysql_size_ diff --git a/plugins/other/mysql_size_all b/plugins/mysql/mysql_size_all similarity index 100% rename from plugins/other/mysql_size_all rename to plugins/mysql/mysql_size_all diff --git a/plugins/other/mysql_slave b/plugins/mysql/mysql_slave similarity index 100% rename from plugins/other/mysql_slave rename to plugins/mysql/mysql_slave diff --git a/plugins/other/mysql_slave_threads b/plugins/mysql/mysql_slave_threads similarity index 100% rename from plugins/other/mysql_slave_threads rename to plugins/mysql/mysql_slave_threads diff --git a/plugins/other/mysql-schema-size b/plugins/mysql_schema_size_/mysql-schema-size similarity index 100% rename from plugins/other/mysql-schema-size rename to plugins/mysql_schema_size_/mysql-schema-size diff --git a/plugins/other/mysql-table-size b/plugins/mysql_table_size_/mysql-table-size similarity index 100% rename from plugins/other/mysql-table-size rename to plugins/mysql_table_size_/mysql-table-size diff --git a/plugins/other/dvb-signal b/plugins/mythtv/dvb-signal similarity index 100% rename from plugins/other/dvb-signal rename to plugins/mythtv/dvb-signal diff --git a/plugins/other/mythtv_programs b/plugins/mythtv/mythtv_programs similarity index 100% rename from plugins/other/mythtv_programs rename to plugins/mythtv/mythtv_programs diff --git a/plugins/other/mythtv_status_ b/plugins/mythtv/mythtv_status_ similarity index 100% rename from plugins/other/mythtv_status_ rename to plugins/mythtv/mythtv_status_ diff --git a/plugins/nagios/nagios_multi_ b/plugins/nagios/nagios_multi_ new file mode 100755 index 00000000..926428bc --- /dev/null +++ b/plugins/nagios/nagios_multi_ @@ -0,0 +1,701 @@ +#!/usr/bin/perl +# +=head1 NAGIOS MULTIGRAPH + +A Plugin to monitor Nagios Servers and their Performance (Multigraph) + +=head1 MUNIN CONFIGURATION + +[nagios_multi_*] + user root + env.binary /usr/local/nagios/bin/nagiostats *default* + env.passive off *default* + +=head2 MUNIN ENVIRONMENT CONFIGURATION EXPLANATION + + binary = location of your nagiostats binary including binary + passive = tell the plugin to graph passive results + +=head1 NODE CONFIGURATION + + Make sure the nagiostats binary exists and is executable by root + or by the user specified that the plugin will run as. + + Available root graphs and subgraphs contained in this Plugin. + + services => I This graphs the current service problems. + svcchkdetail => This graph shows current services warning,critical,unknown,checked,scheduled,flapping,down + svcchkext => This graph shows the service check execution times + svcchklat => This graph shows the service check latency times + svcchksc => This graph shows the serivce check state change % + + hosts => I This graphs the current host problems. + hostchkdetail => This graph shows current hosts down,unreachable,checked,scheduled,flapping,down + hostchkext => This graph shows the host check execution times + hostchklat => This graph shows the host check latency times + hostchksc => This graph shows the host check state change % + + checks => I This graphs the current host problems. + extcmdcount => This graph shows external command buffer availability / usage + hostchkactcount => This graph shows the active host checks for the last 1,5,15,60M + hostchkpsvcount => This graph shows the passive host checks for the last 1,5,15,60M + * depends on passive flag, which defaults to off, and forces these graphs to not be drawn + svcchkactcount => This graph shows the active service checks for the last 1,5,15,60M + svcchkpsvcount => This graph shows the passive service checks for the last 1,5,15,60M + * depends on passive flag, which defaults to off, and forces these graphs to not be drawn + +=head1 MUNIN PLUGIN DOCUMENTATION + + This is just some helpful links for plugin troubleshooting. + + http://munin-monitoring.org/wiki/Documentation#Plugins + http://munin-monitoring.org/wiki/protocol-config + +=head1 AUTHOR + +Matt West < https://github.com/mhwest13/Nagios-Munin-Plugin > + +=head1 LICENSE + +GPLv2 + +=head1 MAGIC MARKERS + +#%# family=auto +#%# capabilities=autoconf suggest + +=cut + +use strict; +use warnings; +use Munin::Plugin; +use File::Basename; + +if (basename($0) !~ /^nagios_multi_/) { + print "This script needs to be named nagios_multi_ and have symlinks which start the same.\n"; + exit 1; +} + +# tell munin about our multigraph capabilties +need_multigraph(); + +# import binary information or use default setting +my $binary = $ENV{binary} || '/usr/local/nagios/bin/nagiostats'; +unless ((-e $binary) && (-x $binary)) { + # err, I'm unable to run the binary specified + print "no: Unable to execute $binary\n"; + exit 1; +} + +# import passive flag or use default setting +my $passive = $ENV{passive} || 'off'; + +=head1 Graph Declarations + + This block of code builds up all of the graph info for all root / sub graphs. + + %graphs: is a container for all of the graph definition information. In here is where you'll + find the configuration information for munin's graphing procedure. + Format: + + $graph{graph_name} => { + config => { + You'll find the main graph config stored here + { key => value }, + { ... }, + }, + keys => [ 'Name', 'Name', 'Name', ... ], + datasrc => [ + Name: name given to data value + Attr: Attribute and value, attribute must be valid plugin argument + { name => 'Name', info => 'info about graph' }, + { ... }, + ], + results => { + You'll find the results info from a stats call stored here + { key => value }, + { ... }, + }, + } + +=cut + +my %graphs; + +# main graph for service checks +$graphs{services} = { + config => { + args => '--lower-limit 0', + vlabel => 'Service Problems', + category => 'nagios', + title => 'Service Problems', + info => 'Current Service Problems by Alert Status', + }, + keys => [ 'NUMSVCOK', 'NUMSVCWARN', 'NUMSVCUNKN', 'NUMSVCCRIT' ], + datasrc => [ + { name => 'NUMSVCOK', label => 'Up', min => '0', type => 'GAUGE', info => 'number of services which are Ok.', graph => 'no', draw => 'LINE2' }, + { name => 'NUMSVCWARN', label => 'Warning', min => '0', type => 'GAUGE', info => 'number of services which are Warning.', draw => 'LINE2' }, + { name => 'NUMSVCUNKN', label => 'Unknown', min => '0', type => 'GAUGE', info => 'number of services which are Unknown.', draw => 'LINE2' }, + { name => 'NUMSVCCRIT', label => 'Critical', min => '0', type => 'GAUGE', info => 'number of services which are Critical.', draw => 'LINE2' }, + ], +}; +# multi-graph for service check detail information ( sub graph of service problems graph ) +$graphs{svcchkdetail} = { + config => { + args => '--lower-limit 0', + vlabel => 'Total # of Service Checks', + category => 'details', + title => 'Detailed Service Info', + info => 'Detailed Service Check Information', + }, + keys => [ 'NUMSVCWARN', 'NUMSVCUNKN', 'NUMSVCCRIT', 'NUMSVCCHECKED', 'NUMSVCSCHEDULED', 'NUMSVCFLAPPING', 'NUMSVCDOWNTIME' ], + datasrc => [ + { name => 'NUMSVCWARN', label => 'Warning', min => '0', type => 'GAUGE', info => 'number of services which are Warning.', draw => 'LINE2' }, + { name => 'NUMSVCUNKN', label => 'Unknown', min => '0', type => 'GAUGE', info => 'number of services which are Unknown.', draw => 'LINE2' }, + { name => 'NUMSVCCRIT', label => 'Critical', min => '0', type => 'GAUGE', info => 'number of services which are Critical.', draw => 'LINE2' }, + { name => 'NUMSVCCHECKED', label => 'Checked', min => '0', type => 'GAUGE', info => 'total number of services that have been checked since start.', draw => 'LINE2' }, + { name => 'NUMSVCSCHEDULED', label => 'Scheduled', min => '0', type => 'GAUGE', info => 'total number of services that are currently scheduled to be checked.', draw => 'LINE2' }, + { name => 'NUMSVCFLAPPING', label => 'Flapping', min => '0', type => 'GAUGE', info => 'total number of services that are currently flapping.', draw => 'LINE2' }, + { name => 'NUMSVCDOWNTIME', label => 'Scheduled Downtime', min => '0', type => 'GAUGE', info => 'total number of services that are currently in scheduled downtime.', draw => 'LINE2' }, + ], +}; +# multi-graph for service check % state change ( sub graph of service problems graph ) +$graphs{svcchksc} = { + config => { + args => '--lower-limit 0 --upper-limit 100', + vlabel => '%', + category => 'statechange', + title => 'Service State Change', + info => 'Total Percent of State Change between checks', + }, + keys => [ 'MINSVCPSC', 'MAXSVCPSC', 'AVGSVCPSC' ], + datasrc => [ + { name => 'MINSVCPSC', label => 'Min', min => '0', type => 'GAUGE', info => 'min service check % state change.', draw => 'AREA' }, + { name => 'MAXSVCPSC', label => 'Max', min => '0', type => 'GAUGE', info => 'max service check % state change.', draw => 'AREA' }, + { name => 'AVGSVCPSC', label => 'Average', min => '0', type => 'GAUGE', info => 'avg service check % state change.', draw => 'LINE2' }, + ], +}; +# multi-graph for service check latency and execution times ( sub graph of service problems graph ) +$graphs{svcchklat} = { + config => { + args => '--lower-limit 0', + vlabel => 'time (ms)', + category => 'latency', + title => 'Service Check Latency Times', + info => 'Service Check Latency Times', + }, + keys => [ 'MINACTSVCLAT', 'MAXACTSVCLAT', 'AVGACTSVCLAT' ], + datasrc => [ + { name => 'MINACTSVCLAT', label => 'Min Latency', min => '0', type => 'GAUGE', info => 'min active service check latency (ms).', draw => 'LINE2' }, + { name => 'MAXACTSVCLAT', label => 'Max Latency', min => '0', type => 'GAUGE', info => 'max active service check latency (ms).', draw => 'LINE2' }, + { name => 'AVGACTSVCLAT', label => 'Average Latency', min => '0', type => 'GAUGE', info => 'avg active service check latency (ms).', draw => 'LINE2' }, + ], +}; +# multi-graph for service check execution time ( sub graph of service problems graph ) +$graphs{svcchkext} = { + config => { + args => '--lower-limit 0', + vlabel => 'time (ms)', + category => 'execution', + title => 'Service Check Execution Times', + info => 'Service Check Execution Times', + }, + keys => [ 'MINACTSVCEXT', 'MAXACTSVCEXT', 'AVGACTSVCEXT' ], + datasrc => [ + { name => 'MINACTSVCEXT', label => 'Min Execution', min => '0', type => 'GAUGE', info => 'min active service check execution time (ms).', draw => 'LINE2' }, + { name => 'MAXACTSVCEXT', label => 'Max Execution', min => '0', type => 'GAUGE', info => 'max active service check execution time (ms).', draw => 'LINE2' }, + { name => 'AVGACTSVCEXT', label => 'Average Execution', min => '0', type => 'GAUGE', info => 'avg active service check execution time (ms).', draw => 'LINE2' }, + ], +}; +# main graph for host problems +$graphs{hosts} = { + config => { + args => '--lower-limit 0', + vlabel => 'Host Problems', + category => 'nagios', + title => 'Host Problems', + info => 'Current Host Problems by Alert Status', + }, + keys => [ 'NUMHSTUP', 'NUMHSTDOWN', 'NUMHSTUNR' ], + datasrc => [ + { name => 'NUMHSTUP', label => 'Up', min => '0', type => 'GAUGE', info => 'number of hosts up.', graph => 'no', draw => 'LINE2' }, + { name => 'NUMHSTDOWN', label => 'Down', min => '0', type => 'GAUGE', info => 'number of hosts which are down.', draw => 'LINE2' }, + { name => 'NUMHSTUNR', label => 'Unknown', min => '0', type => 'GAUGE', info => 'number of hosts which are Unreachable.', draw => 'LINE2' }, + ], +}; +# multi-graph for host check detail information ( sub graph of host problems graph ) +$graphs{hostchkdetail} = { + config => { + args => '--lower-limit 0', + vlabel => 'Total # of Host Checks', + category => 'details', + title => 'Detailed Host Info', + info => 'Detailed Host Check Information', + }, + keys => [ 'NUMHSTDOWN', 'NUMHSTUNR', 'NUMHSTCHECKED', 'NUMHSTSCHEDULED', 'NUMHSTFLAPPING', 'NUMHSTDOWNTIME' ], + datasrc => [ + { name => 'NUMHSTDOWN', label => 'Down', min => '0', type => 'GAUGE', info => 'number of hosts which are down.', draw => 'LINE2' }, + { name => 'NUMHSTUNR', label => 'Unknown', min => '0', type => 'GAUGE', info => 'number of hosts which are Unreachable.', draw => 'LINE2' }, + { name => 'NUMHSTCHECKED', label => 'Checked', min => '0', type => 'GAUGE', info => 'total number of hosts that have been checked since start.', draw => 'LINE2' }, + { name => 'NUMHSTSCHEDULED', label => 'Scheduled', min => '0', type => 'GAUGE', info => 'total number of hosts that are currently scheduled to be checked.', draw => 'LINE2' }, + { name => 'NUMHSTFLAPPING', label => 'Flapping', min => '0', type => 'GAUGE', info => 'total number of hosts that are currently flapping.', draw => 'LINE2' }, + { name => 'NUMHSTDOWNTIME', label => 'Downtime', min => '0', type => 'GAUGE', info => 'total number of hosts that are currently in scheduled downtime.', draw => 'LINE2' }, + ], +}; +# multi-graph for host check % state change ( sub graph of host problems graph ) +$graphs{hostchksc} = { + config => { + args => '--lower-limit 0 --upper-limit 100', + vlabel => '%', + category => 'statechange', + title => 'Host State Change', + info => 'Total Percent of State Change between checks', + }, + keys => [ 'MINHSTPSC', 'MAXHSTPSC', 'AVGHSTPSC' ], + datasrc => [ + { name => 'MINHSTPSC', label => 'Min', min => '0', type => 'GAUGE', info => 'min host check % state change.', draw => 'AREA' }, + { name => 'MAXHSTPSC', label => 'Max', min => '0', type => 'GAUGE', info => 'max host check % state change.', draw => 'AREA' }, + { name => 'AVGHSTPSC', label => 'Average', min => '0', type => 'GAUGE', info => 'avg host check % state change.', draw => 'LINE2' }, + ], +}; +# multi-graph for host check latency times ( sub graph of host problems graph ) +$graphs{hostchklat} = { + config => { + args => '--lower-limit 0', + vlabel => 'time (ms)', + category => 'latency', + title => 'Host Check Latency Times', + info => 'Host Check Latency Times', + }, + keys => [ 'MINACTHSTLAT', 'MAXACTHSTLAT', 'AVGACTHSTLAT' ], + datasrc => [ + { name => 'MINACTHSTLAT', label => 'Min Latency', min => '0', type => 'GAUGE', info => 'min active host check latency (ms).', draw => 'LINE2' }, + { name => 'MAXACTHSTLAT', label => 'Max Latency', min => '0', type => 'GAUGE', info => 'max active host check latency (ms).', draw => 'LINE2' }, + { name => 'AVGACTHSTLAT', label => 'Average Latency', min => '0', type => 'GAUGE', info => 'avg active host check latency (ms).', draw => 'LINE2' }, + ], +}; +# multi-graph for host check execution times ( sub graph of host problems graph ) +$graphs{hostchkext} = { + config => { + args => '--lower-limit 0', + vlabel => 'time (ms)', + category => 'execution', + title => 'Host Check Execution Times', + info => 'Host Check Execution Times', + }, + keys => [ 'MINACTHSTEXT', 'MAXACTHSTEXT', 'AVGACTHSTEXT' ], + datasrc => [ + { name => 'MINACTHSTEXT', label => 'Min Execution', min => '0', type => 'GAUGE', info => 'min active host check execution time (ms).', draw => 'LINE2' }, + { name => 'MAXACTHSTEXT', label => 'Max Execution', min => '0', type => 'GAUGE', info => 'max active host check execution time (ms).', draw => 'LINE2' }, + { name => 'AVGACTHSTEXT', label => 'Average Execution', min => '0', type => 'GAUGE', info => 'avg active host check execution time (ms).', draw => 'LINE2' }, + ], +}; +# main graph for host / service check counts +$graphs{checks} = { + config => { + args => '--lower-limit 0', + vlabel => 'Total # of Checks', + category => 'nagios', + title => 'Totals', + info => 'Total Number of Service and Host Checks', + }, + keys => [ 'NUMSERVICES', 'NUMHOSTS' ], + datasrc => [ + { name => 'NUMSERVICES', label => '# of Services', min => '0', type => 'GAUGE', info => 'total number of services.', draw => 'LINE2' }, + { name => 'NUMHOSTS', label => '# of Hosts', min => '0', type => 'GAUGE', info => 'total number of hosts.', draw => 'LINE2' }, + ], +}; +# multi-graph for number of host checks in x mins ( sub graph of checks graph ) +$graphs{hostchkactcount} = { + config => { + args => '--lower-limit 0', + vlabel => '# Host Checks', + category => 'active', + title => 'Host Checks', + info => 'Total Number of Active Host Checks', + order => 'NUMHSTACTCHK60M NUMHSTACTCHK15M NUMHSTACTCHK5M NUMHSTACTCHK1M', + }, + keys => [ 'NUMHSTACTCHK1M', 'NUMHSTACTCHK5M', 'NUMHSTACTCHK15M', 'NUMHSTACTCHK60M' ], + datasrc => [ + { name => 'NUMHSTACTCHK1M', label => 'Active Checks 1m', min => '0', type => 'GAUGE', info => 'number of hosts actively checked in last 1 minutes.', draw => 'AREA' }, + { name => 'NUMHSTACTCHK5M', label => 'Active Checks 5m', min => '0', type => 'GAUGE', info => 'number of hosts actively checked in last 5 minutes.', draw => 'AREA' }, + { name => 'NUMHSTACTCHK15M', label => 'Active Checks 15m', min => '0', type => 'GAUGE', info => 'number of hosts actively checked in last 15 minutes.', draw => 'AREA' }, + { name => 'NUMHSTACTCHK60M', label => 'Active Checks 60m', min => '0', type => 'GAUGE', info => 'number of hosts actively checked in last 60 minutes.', draw => 'AREA' }, + ], +}; +# multi-graph for number of host checks in x mins ( sub graph of checks graph ) +$graphs{hostchkpsvcount} = { + config => { + args => '--lower-limit 0', + vlabel => '# Host Checks', + category => 'passive', + title => 'Host Checks', + info => 'Total Number of Passive Host Checks', + order => 'NUMHSTPSVCHK60M NUMHSTPSVCHK15M NUMHSTPSVCHK5M NUMHSTPSVCHK1M', + }, + keys => [ 'NUMHSTPSVCHK1M', 'NUMHSTPSVCHK5M', 'NUMHSTPSVCHK15M', 'NUMHSTPSVCHK60M' ], + datasrc => [ + { name => 'NUMHSTPSVCHK1M', label => 'Passive Checks 1m', min => '0', type => 'GAUGE', info => 'number of hosts passively checked in last 1 minutes.', draw => 'AREA' }, + { name => 'NUMHSTPSVCHK5M', label => 'Passive Checks 5m', min => '0', type => 'GAUGE', info => 'number of hosts passively checked in last 5 minutes.', draw => 'AREA' }, + { name => 'NUMHSTPSVCHK15M', label => 'Passive Checks 15m', min => '0', type => 'GAUGE', info => 'number of hosts passively checked in last 15 minutes.', draw => 'AREA' }, + { name => 'NUMHSTPSVCHK60M', label => 'Passive Checks 60m', min => '0', type => 'GAUGE', info => 'number of hosts passively checked in last 60 minutes.', draw => 'AREA' }, + ], +}; +# multi-graph for number of service checks in x mins ( sub graph of checks graph ) +$graphs{svcchkactcount} = { + config => { + args => '--lower-limit 0', + vlabel => '# of Service Checks', + category => 'active', + title => 'Service Checks', + info => 'Total Number of Active Service Checks', + order => 'NUMSVCACTCHK60M NUMSVCACTCHK15M NUMSVCACTCHK5M NUMSVCACTCHK1M', + }, + keys => [ 'NUMSVCACTCHK1M', 'NUMSVCACTCHK5M', 'NUMSVCACTCHK15M', 'NUMSVCACTCHK60M' ], + datasrc => [ + { name => 'NUMSVCACTCHK1M', label => 'Active Checks 1m', min => '0', type => 'GAUGE', info => 'number of services actively checked in last 1 minutes.', draw => 'AREA' }, + { name => 'NUMSVCACTCHK5M', label => 'Active Checks 5m', min => '0', type => 'GAUGE', info => 'number of services actively checked in last 5 minutes.', draw => 'AREA' }, + { name => 'NUMSVCACTCHK15M', label => 'Active Checks 15m', min => '0', type => 'GAUGE', info => 'number of services actively checked in last 15 minutes.', draw => 'AREA' }, + { name => 'NUMSVCACTCHK60M', label => 'Active Checks 60m', min => '0', type => 'GAUGE', info => 'number of services actively checked in last 60 minutes.', draw => 'AREA' }, + ], +}; +# multi-graph for number of service checks in x mins ( sub graph of checks graph ) +$graphs{svcchkpsvcount} = { + config => { + args => '--lower-limit 0', + vlabel => '# of Service Checks', + category => 'passive', + title => 'Service Checks', + info => 'Total Number of Passive Service Checks', + order => 'NUMSVCPSVCHK60M NUMSVCPSVCHK15M NUMSVCPSVCHK5M NUMSVCPSVCHK1M', + }, + keys => [ 'NUMSVCPSVCHK1M', 'NUMSVCPSVCHK5M', 'NUMSVCPSVCHK15M', 'NUMSVCPSVCHK60M' ], + datasrc => [ + { name => 'NUMSVCPSVCHK1M', label => 'Passive Checks 1m', min => '0', type => 'GAUGE', info => 'number of services passively checked in last 1 minutes.', draw => 'AREA' }, + { name => 'NUMSVCPSVCHK5M', label => 'Passive Checks 5m', min => '0', type => 'GAUGE', info => 'number of services passively checked in last 5 minutes.', draw => 'AREA' }, + { name => 'NUMSVCPSVCHK15M', label => 'Passive Checks 15m', min => '0', type => 'GAUGE', info => 'number of services passively checked in last 15 minutes.', draw => 'AREA' }, + { name => 'NUMSVCPSVCHK60M', label => 'Passive Checks 60m', min => '0', type => 'GAUGE', info => 'number of services passively checked in last 60 minutes.', draw => 'AREA' }, + ], +}; +# multi-graph for external command count ( sub graph of checks graph ) +$graphs{extcmdcount} = { + config => { + args => '--lower-limit 0', + vlabel => '# of Ext Command Slots', + category => 'externalcmds', + title => 'External Commands', + info => 'External Command Buffer Slot Information', + }, + keys => [ 'TOTCMDBUF', 'USEDCMDBUF', 'HIGHCMDBUF', 'NUMEXTCMDS1M', 'NUMEXTCMDS5M', 'NUMEXTCMDS15M' ], + datasrc => [ + { name => 'TOTCMDBUF', label => 'Total', min => '0', type => 'GAUGE', info => 'total number of external command buffer slots available.', draw => 'AREA' }, + { name => 'USEDCMDBUF', label => 'Current Used', min => '0', type => 'GAUGE', info => 'number of external command buffer slots currently in use.', draw => 'LINE2' }, + { name => 'HIGHCMDBUF', label => 'Peak Used', min => '0', type => 'GAUGE', info => 'highest number of external command buffer slots ever in use.', draw => 'LINE2' }, + { name => 'NUMEXTCMDS1M', label => 'Used last 1m', min => '0', type => 'GAUGE', info => 'number of external commands processed in last 1 minutes.', draw => 'LINE2' }, + { name => 'NUMEXTCMDS5M', label => 'Used last 5m', min => '0', type => 'GAUGE', info => 'number of external commands processed in last 5 minutes.', draw => 'LINE2' }, + { name => 'NUMEXTCMDS15M', label => 'Used last 15m', min => '0', type => 'GAUGE', info => 'number of external commands processed in last 15 minutes.', draw => 'LINE2' }, + ], +}; + +=head1 Munin Checks + + These checks look for config / autoconf / suggest params + +=head2 Config Check + + This block of code looks at the argument that is possibly supplied, + should it be config, it then checks to make sure the plugin + specified exists, assuming it does, it will run the do_config + subroutine for the plugin specified, otherwise it dies complaining + about an unknown plugin. + +=cut + +if (defined $ARGV[0] && $ARGV[0] eq 'config') { + # Lets take the plugin from the execution name. + $0 =~ /nagios_multi_(.+)*/; + my $plugin = $1; + # And lets make sure we have a plugin called that. + die 'Unknown Plugin Specified: ' . ($plugin ? $plugin : '') unless $graphs{$plugin}; + # Now lets go ahead and print out our config. + do_config($plugin); + exit 0; +} + +=head2 Autoconf Check + + This block of code looks at the argument that is possibly supplied, + should it be autoconf, we are going to print yes at this point since + we've already tested for our binary to exist and be executable, the + process will then exit. + +=cut + +if (defined $ARGV[0] && $ARGV[0] eq 'autoconf') { + # well we can execute the binary, so plugin should be good from here... + print "yes\n"; + exit 0; +} + +=head2 Suggest Check + + This block of code looks at the argument that is possibly supplied, + should it be suggest, we are going to print the possible plugins + which can be specified. Note we only specify the root graphs for the + multigraphs, since the rest of the subgraphs will appear "behind" the + root graphs. + +=cut + +if (defined $ARGV[0] && $ARGV[0] eq 'suggest') { + # well we can execute the binary, so print possible root multigraph plugin names + my @rootplugins = ('services','hosts','checks'); + foreach my $plugin (@rootplugins) { + print "$plugin\n"; + } + exit 0; +} + +=head1 Subroutines + + Begin Subroutine calls to output data / config information + +=head2 fetch_output + + This subroutine is the main call for printing data for the plugin. + No parameters are taken as this is the default call if no arguments + are supplied from the command line. + +=cut + +fetch_output(); + +sub fetch_output { + # Lets figure out what plugin they want to run, and check that it exists + $0 =~ /nagios_multi_(.+)*/; + my $plugin = $1; + die 'Unknown Plugin Specified: ' . ($plugin ? $plugin : '') unless $graphs{$plugin}; + # Lets set up our subgraphs array with all of the graphs which are extensions + # of the root graph / plugin + my @subgraphs; + if ($plugin eq 'services') { + @subgraphs = ('svcchkdetail','svcchksc','svcchklat','svcchkext'); + } elsif ($plugin eq 'hosts') { + @subgraphs = ('hostchkdetail','hostchksc','hostchklat','hostchkext'); + } elsif ($plugin eq 'checks') { + @subgraphs = ('svcchkactcount','hostchkactcount','extcmdcount'); + if ($passive =~ /on/i) { + push(@subgraphs,'svcchkpsvcount'); + push(@subgraphs,'hostchkpsvcount'); + } + } + # Lets just double check the plugin you specified is a root graph / plugin + if (grep $_ eq $plugin, @subgraphs) { + die "Error: $plugin is not a valid root graph, valid graphs are: @subgraphs\n"; + } + # Lets print out the data for our sub graphs / plugins + foreach my $subgraph (@subgraphs) { + print_sub_output($plugin,$subgraph); + } + # Lets print out the data for our main graph / plugin + print_root_output($plugin); + return; +} + +=head2 print_root_output + + This block of code prints out the return values for our root graphs. It takes + one parameter $plugin. Returns when completed + + $plugin; main(root) graph we are calling up to print data values for + + Example: print_root_output($plugin); + +=cut + +sub print_root_output { + # Lets get our plugin, set our graph information, and print for Munin to process + my ($plugin) = (@_); + my $graph = $graphs{$plugin}; + print "multigraph nagios_$plugin\n"; + # Getting keys to pass to nagiostats for data retrieval + # call up fetch_nagios_stats with the keys we just got. + my @keys = @{$graph->{keys}}; + fetch_nagios_stats($plugin,@keys); + # print the results for the keys with the name for Munin to process + foreach my $dsrc (@{$graph->{datasrc}}) { + my $output = 0; + my %datasrc = %$dsrc; + while ( my ($key, $value) = each(%datasrc)) { + next if ($key ne 'name'); + print "$dsrc->{name}.value $graph->{results}->{$value}\n"; + } + } + return; +} + +=head2 print_sub_output + + This block of code prints out the return values for our root graphs. It takes + one parameter $plugin. Returns when completed + + $plugin; main(root) being called, used for multigraph output + $subgraph; graph we are actually trying to print data values for + + Example: print_sub_output($plugin,$subgraph); + +=cut + +sub print_sub_output { + # Lets get our plugin, set our graph information, and print for Munin to process + my ($plugin,$subgraph) = (@_); + my $graph = $graphs{$subgraph}; + print "multigraph nagios_$plugin\.$subgraph\n"; + # Getting keys to pass to nagiostats for data retrieval + # call up fetch_nagios_stats with the keys we just got. + my @keys = @{$graph->{keys}}; + fetch_nagios_stats($subgraph,@keys); + # print the results for the keys with the name for Munin to process + foreach my $dsrc (@{$graph->{datasrc}}) { + my $output = 0; + my %datasrc = %$dsrc; + while ( my ($key, $value) = each(%datasrc)) { + next if ($key ne 'name'); + print "$dsrc->{name}.value $graph->{results}->{$value}\n"; + } + } + return; +} + +=head2 do_config + + This is the main call issued assuming we call up config and plugin specified exists + The subroutine takes one parameter $plugin, and returns when completed. + + $plugin; main(root) graph being called + + Example: do_config($plugin); + +=cut + +sub do_config { + # Lets get our plugin and set subgraphs to undef + my ($plugin) = (@_); + my @subgraphs; + if ($plugin eq 'services') { + # update subgraphs since our plugin is services + @subgraphs = ('svcchkdetail','svcchksc','svcchklat','svcchkext'); + } elsif ($plugin eq 'hosts') { + # update subgraphs since our plugin is hosts + @subgraphs = ('hostchkdetail','hostchksc','hostchklat','hostchkext'); + } elsif ($plugin eq 'checks') { + # update subgraphs since our plugin is checks + @subgraphs = ('svcchkactcount','hostchkactcount','extcmdcount'); + if ($passive =~ /on/i) { + push(@subgraphs,'svcchkpsvcount'); + push(@subgraphs,'hostchkpsvcount'); + } + } + # Now that we know what graphs to reference, lets print out their config info + foreach my $subgraph (@subgraphs) { + print_sub_config($plugin,$subgraph); + } + # Now lets print out the config information for our root graph + print_root_config($plugin); + return; +} + +=head2 print_sub_config + + This subroutine prints out the config information for all of the subgraphs. + It takes two parameters, $plugin and $subgraph + + $plugin; main(root) graph used for multigraph call + $subgraph; subgraph being called up. + + Example: print_sub_config($plugin,$subgraph); + +=cut + +sub print_sub_config { + # Lets get our plugin and subgraph, after that print for Munin to process it. + my ($plugin,$subgraph) = (@_); + my $graph = $graphs{$subgraph}; + print "multigraph nagios_$plugin.$subgraph\n"; + # Lets print our subgraph's main config info. + my %graphconf = %{$graph->{config}}; + while ( my ($key, $value) = each(%graphconf)) { + print "graph_$key $value\n"; + } + # Lets print our subgraph's per graph config info. + foreach my $dsrc (@{$graph->{datasrc}}) { + my %datasrc = %$dsrc; + while ( my ($key, $value) = each(%datasrc)) { + next if ($key eq 'name'); + print "$dsrc->{name}.$key $value\n"; + } + } + return; +} + +=head2 print_root_config + + This subroutine prints out the config information for all of the main(root) graphs. + It takes one parameters, $plugin + + $plugin; main(root) graph used for multigraph call + + Example: print_root_config($plugin); + +=cut + +sub print_root_config { + # Lets get our plugin and graph, after that print for Munin to process it. + my ($plugin) = (@_); + my $graph = $graphs{$plugin}; + print "multigraph nagios_$plugin\n"; + # Lets print out graph's main config info. + my %graphconf = %{$graph->{config}}; + while ( my ($key, $value) = each(%graphconf)) { + print "graph_$key $value\n"; + } + # Lets print our graphs per graph config info. + foreach my $dsrc (@{$graph->{datasrc}}) { + my %datasrc = %$dsrc; + while ( my ($key, $value) = each(%datasrc)) { + next if ($key eq 'name'); + print "$dsrc->{name}.$key $value\n"; + } + } + return; +} + +=head2 fetch_nagios_stats + + This subroutine actually runs the nagiostats binary with the keys specified in an array + Two parameters are passed, $plugin and @keys, and it will return when complete. + + $plugin; graph we are calling up, we use this to store the results in the hash + for easy recall later. + @keys; keys we want the values for from nagiostats binary. + + Example: fetch_nagios_stats($plugin,@keys); + +=cut + +sub fetch_nagios_stats { + # Lets get our current plugin and list of keys we want info for, as well as reference our graph + my ($plugin,@keys) = (@_); + my $graph = $graphs{$plugin}; + # Lets set our command to include our binary plus options, as well as join our array with ,'s + my $command = $binary . " -m -d " . join(",",@keys); + # Lets open the command and pipe it out for easy reading by line + open(CMD, "$command |") or die "Unable to execute command: $command\n"; + # While a return exists from the command, store the value in the key specified + while (my $line = ) { + chomp($line); + my $key = shift(@keys); + $graph->{results}->{$key} = $line; + } + return; +} diff --git a/plugins/other/nagiosstatus b/plugins/nagios/nagiosstatus similarity index 100% rename from plugins/other/nagiosstatus rename to plugins/nagios/nagiosstatus diff --git a/plugins/other/netapp_cifs b/plugins/netapp/netapp_cifs similarity index 100% rename from plugins/other/netapp_cifs rename to plugins/netapp/netapp_cifs diff --git a/plugins/other/netapp_cpu_ b/plugins/netapp/netapp_cpu_ similarity index 100% rename from plugins/other/netapp_cpu_ rename to plugins/netapp/netapp_cpu_ diff --git a/plugins/other/netapp_if_ b/plugins/netapp/netapp_if_ similarity index 100% rename from plugins/other/netapp_if_ rename to plugins/netapp/netapp_if_ diff --git a/plugins/other/cirix-netscaler-connections b/plugins/netscaler/cirix-netscaler-connections similarity index 100% rename from plugins/other/cirix-netscaler-connections rename to plugins/netscaler/cirix-netscaler-connections diff --git a/plugins/other/cirix-netscaler-cpu-usage b/plugins/netscaler/cirix-netscaler-cpu-usage similarity index 100% rename from plugins/other/cirix-netscaler-cpu-usage rename to plugins/netscaler/cirix-netscaler-cpu-usage diff --git a/plugins/other/ag241-adsl b/plugins/network/ag241-adsl similarity index 100% rename from plugins/other/ag241-adsl rename to plugins/network/ag241-adsl diff --git a/plugins/other/arp b/plugins/network/arp similarity index 100% rename from plugins/other/arp rename to plugins/network/arp diff --git a/plugins/other/avm-fritzbox-wan-traffic b/plugins/network/avm-fritzbox-wan-traffic similarity index 100% rename from plugins/other/avm-fritzbox-wan-traffic rename to plugins/network/avm-fritzbox-wan-traffic diff --git a/plugins/network/bandwidth_ b/plugins/network/bandwidth_ new file mode 100755 index 00000000..99a4fc39 --- /dev/null +++ b/plugins/network/bandwidth_ @@ -0,0 +1,284 @@ +#!/usr/bin/perl +# -*- perl -*- + +=head1 NAME + +bandwidth_ - Wildcard-plugin to monitor total network traffic and + predict 30 day bandwidth usage + +=head1 CONFIGURATION + +This is a wildcard plugin. To monitor an interface, link +bandwidth_ to this file. E.g. + + ln -s /usr/share/munin/node/plugins-auto/bandwidth_ \ + /etc/munin/node.d/bandwidth_eth0 + +...will monitor eth0 + +Most likely usage is to monitor an interface connected to your ISP. + +The suggest option will try and determine if you have any interfaces with a +public IP and if so it will suggest monitoring those interfaces. If all +IP addresses are private the setup will have to be done manually. Suggest +does not handle IPv6 addresses. + +=head1 USAGE + +Any device found in /proc/net/dev can be monitored. Examples include ipsec*, +eth*, irda* and lo. + +Please note that aliases cannot be monitored with this plugin. + +=head1 VERSION + +$Id: bandwidth_,v 1.35 2012/01/23 20:04:33 root Exp $ + +=head1 AUTHOR + +Sean Whitney + +=head1 LICENSE + +GPLv2 + +=head1 MAGIC MARKERS + + #%# family=contrib + #%# capabilities=autoconf suggest + +=head1 BUGS + +I know that bandwidth is bits and base10 as opposed to bytes and base2. +However the purpose of this plugin it to monitor your monthly bandwidth +consumption to make sure you don't go over your ISP's peak. ISP's seem +to be interested in expressing peaks in bytes.... + +=cut + +use strict; +use Storable qw(store retrieve); +use Switch; + +my $interface; +my $history; +my $counter_input; +my $counter_output; +my $input; +my $output; +my $uptime; +my $oldest_ts; +my $input_30days; +my $output_30days; +my $perf_ref = {}; +my $count30 = 2592000; # The number of seconds in 30 days +my $unix_ts = time; +my $rollover = 4294967295; + +eval { init(); }; + +sub autoconf { + $0 =~ /bandwidth_(.+)*$/; + $interface = $1; + exit 2 unless defined $interface; + $history = "/var/lib/munin/plugin-state/bandwidth_$interface.state"; +} + +sub bit32or64 { + if ( $input > $rollover || $output > $rollover ) { + $rollover = 18446744073709551615; + } +} + +sub retrieve_history { + return (undef) unless ( -r $history ); + my $store = retrieve($history); + while ( my ( $key, $value ) = each(%$store) ) { + if ( $unix_ts - $key < $count30 ) { + $perf_ref->{$key} = $value; + } + if ( $key =~ /last/ ) { + $perf_ref->{$key} = $value; + } + + } +} + +sub suggest { + + # This only works if one of your interfaces has a public IP, + # Otherwise it will fail and you will have to set it manually + # Multiple public IP addresses can be detected. It won't + # Detect IPv6 addresses. + my $locate = readpipe("locate -b '\\ifconfig'"); + my @ifconfig = readpipe($locate); + my @old; + my $net = "/proc/net/dev"; + my @interfaces; + -f $net || die "Unable to read $net: $!"; + open( DEV, "<", $net ) || die "Unable to read $net: $!"; + + while () { + chomp; + split; + /Inter|face/ and next; + split /:/; + push( @interfaces, $_[0] ); + } + close(DEV); + + foreach (@ifconfig) { + if (/inet addr:([\d.]+)/) { + $1 + =~ /^(127\.\d+|10\.\d+|172\.(1[6-9]|2\d|3[0-1])|192\.168)(\.\d+){2}$/ + and next; + exists $interfaces[ $old[0] ] and print "$old[0]\n"; + } + @old = split; + chomp @old; + } + exit 0; +} + +sub store_history { + + # Store the current values to the new old times + $perf_ref->{$unix_ts} = { + input => $input, + output => $output, + }; + $perf_ref->{last} = { + counter_input => $counter_input, + counter_output => $counter_output, + uptime => $uptime, + }; + store( $perf_ref, $history ) || die "Unable to store $history: $!"; +} + +sub arg { + defined( $ARGV[0] ) or return; + switch ( $ARGV[0] ) { + case 'autoconf' { print "yes\n"; exit 0; } + case 'config' { print_config(); } + case 'suggest' { suggest(); } + } +} + +sub print_config { + print <; + chomp $counter_input; + close($rx); + open(my $tx , "<", "/sys/class/net/$interface/statistics/tx_bytes" ) + || die "Unable to read: $!"; + $counter_output = <$tx>; + chomp $counter_output; + close(DEV); +} + +sub uptime { + my $puptime = "/proc/uptime"; + open( TIME, "<", $puptime ) || die "Unable to read $puptime: $!"; + while (