# Shared functions ## Init All scripts start with sourcing a shared bash file ```shell . $( dirname $0 )/inc_pluginfunctions ``` In that script are several functions starting with prefix **ph.** (=plugin helper) ## Available functions This is a list in alphabetic order ### ph.abort Shows error message and exit with status unknown. Syntax: ```text ph.abort [TEXT] ``` Parameters: 1. TEXT {string} The text message to show Example: ```shell if ! data=$( sudo /bin/ceph df 2>&1 ) then echo "$data" ph.abort "UNKNOWN: ceph is not available or no sudo permissions to execute ceph commands." fi ``` ### ph.execIfReady Execute a command and repeat max. MAXTRIES times if it fails. Syntax: ```text ph.execIfReady [FUNCTION] [ [WAITTIME] [MAXTRIES] ] ``` Parameters: 1. FUNCTION {string} - command line to execute 2. WAITTIME {integer} - optional: sleeptime in sec before repeating again; default: 5 3. MAXTRIES {integer} - optional: max number of tries; default: 3 Example: ```shell ph.execIfReady "timedatectl show >$tmpfile; grep '^NTPSynchronized' $tmpfile >/dev/null" cat $tmpfile | grep "^NTPSynchronized" >/dev/null if [ $? -ne 0 ]; then ph.setStatus "unknown" ph.status "timesync: timedatectl has no line NTP synchronized" cat $tmpfile else cat $tmpfile | grep "^NTPSynchronized=yes" >/dev/null if [ $? -eq 0 ]; then ph.status "timesync: a timesync service is active on this ${myos} host" else ph.setStatus "critical" ph.status "timesync: there is no active timesync - you need to activate ntpd or timesyncd on this ${myos} host" fi fi # /timedatectl ``` ### ph.exit Use at the end to send performance data and exit plugin with set statuscode. This is the last line of your check script. Syntax: ```text ph.exit ``` (no parameters) ### ph.getFileAge get age of a given file in sec The file must be reachable by the monitoring user. Syntax: ```text ph.getFileAge [FILE] ``` Parameters: 1. FILE {string} - filename ### ph.getOS get operating system as lowercase - centos/ debian/ ubuntu ... Syntax: ```text ph.getOS ``` (no parameters) Example: ```shell $ bash -c ". inc_pluginfunctions; ph.getOS" manjaro ``` In a script: ```shell distro=$( ph.getOS ) case $distro in "centos"|"almalinux") # ... do something ;; "debian"|"ubuntu") # ... do something ;; *) ph.abort "UNKNOWN: distro [$distro] was detected but is not supported (yet)." ;; esac ``` ### ph.getOSMajor get OS Major version as integer, i.e. 7 on a CentOS7 Syntax: ```text ph.getOSMajor ``` (no parameters) ### ph.getValueWithParam Return default value or its override from command line. Syntax: ```text ph.getFileAge VALUE PARAMNAME "$@" ``` Parameters: 1. VALUE {integer} - the default value if the parameter (2nd param) was not set in the command line 2. PARAMNAME {char} - a single letter for the parameter to search 3. PARAM LIST {string} - list of all parameters to check; use "$@" set all current params from command line Example: ```shell # set default / override from command line params typeset -i iWarnLimit=$( ph.getValueWithParam 75 w "$@") typeset -i iCriticalLimit=$( ph.getValueWithParam 90 c "$@") ``` This will set variable iWarnLimit based on CLI parameter -w [value] ... if it does not exist it gets the default 75. ### ph.hasParamoption check if a letter was used as command line option and return as 0 (=true) or 1 (=false) Syntax: ```text ph.hasParamoption PARAMNAME "$@" ``` Parameters: 1. PARAMNAME{char} - a single letter for the parameter to search 2. PARAM LIST{string} - list of all parameters to check; use "$@" set all current params from command line Example: Show a help if command line param ``-h`` was given - or no parameter. ```bash ph.hasParamoption "h" "$@" ; bOptHelp=$? if [ $bOptHelp -eq 0 -o $# -lt 1 ]; then _usage exit 0 fi ``` ### ph.perfadd Add performance data. Their output will be written with ```ph.exit```. So you are free to add perfomance data anywhere within your check script. Syntax: ```txt ph.perfadd LABEL VALUE [ WARNLEVEL CRITICAL [ MIN MAX ] ] ``` Parameters: 1. LABEL {string} - a label for the performance value; it must be unique for your script; The given value will be cleaned to lowercase; other chars than a-z, 0-9, minus will be deleted. 2. VALUE {integer|float} - your value; default (if missing): 0 3. WARNLEVEL {integer} - optional: warning level; not handled by graphite; default: empty string 4. CRITICAL {integer} - optional: critical level; not handled by graphite; default: empty string 5. MIN {integer} - optional: minimum value of graph; default: empty string 6. MAX {integer} - optional: maximum value of graph;; default: empty string Example: Add values with label and value only: ```shell data2=$( echo "$netdata" | sort | uniq -c ) iEst=$( echo "$data2" | grep ESTABLISHED | awk '{ print $1 }' ) iListen=$( echo "$data2" | grep LISTEN | awk '{ print $1 }' ) iWait=$( echo "$data2" | grep TIME_WAIT | awk '{ print $1 }' ) ph.perfadd "established" "$iEst" ph.perfadd "listen" "$iListen" ph.perfadd "time-wait" "$iWait" ph.exit ``` Add values and define limits for the graph: I will draw it from 0 to a fixed maximum value like for a given physical maximum or 100 for percent values. Remark that here are empty values for warning and critical to skip them. ```shell ph.perfadd "memory-total" "${ramTotal}MB" "" "" 0 ${ramTotal} ph.perfadd "memory-used" "${ramUsed}MB" "" "" 0 ${ramTotal} ph.perfadd "memory-avail" "${ramAvail}MB" "" "" 0 ${ramTotal} ph.exit ``` ### ph.perfdeltaspeed For increasing system counters: get changerate per second or per minute since last check. Syntax: ```text ph.perfdeltaspeed VARNAME VALUE [ UNIT [isfloat] ] ``` Parameters: 1. VARNAME {string} - an identifier for the value. It is needed to store the last given value and read it on next request. 2. VALUE {integer} - your counter value 3. UNIT {string} - optional: set a unit value can be * "s" or "sec" - for seconds (default) * "m" or "min" - for minutes 4. isfloat {string} - optional: flag to return a float value; set a non empty string for true. Example: ```txt # speed in byte per sec based on last stored value and its age iSpeedRead=` ph.perfdeltaspeed "netio-${myinterface}-rx" $iRead` ``` ### ph.perfshow dump performance data (if u are not using ph.exit) Syntax: ```text ph.perfshow ``` (no parameters) ### ph.require check if a binary PROG exists in search path (=are installed) - if not then execution stops with showing a warning message and status unknown (using ph.abort). Syntax: ```text ph.require [PROG [...PROG_N]] ``` Parameters: 1. PROG - name of program to find in path Example: `ph.require bc lsblk` Hint: Do not place the requirement check before processing -h to show a help. The help should be visible in any case. ### ph.setStatus Set a return status of your check with a keyword. This is easier to handle and to read than fiddling with Nagios exitcodes. You can override it as often you want during the script. Based on the last setting the ``ph.exit`` function will set the exitcode. Syntax: ```text ph.setStatus [STATUS] ``` Parameters: 1. STATUS {string} - a keyword for the return status. * ok * warning * critical * unknown You get an error message when using another keyword. The default value - if you do not set it anywhere - is "ok". Example: ```shell if [ $iMyValue -lt $iWarnLimit ]; then ph.setStatus "ok" else if [ $iMyValue -ge $iCriticalLimit ]; then ph.setStatus "critical" else ph.setStatus "warning" fi fi ph.status "Return value was $iMyValue" ph.exit ``` ### ph.setStatusByLimit Set statuscode by verifying integer only(!) value with critical and warning limit. Syntax: ```text ph.setStatusByLimit VALUE WARNLIMIT CRITLIMIT ``` Parameters: 1. VALUE {integer} - your discovered value 2. WARNLIMIT {integer} - warning limit 3. CRITLIMIT {integer} - critical limit This function works in both directions: * critcal value is HIGHER than warning value; eg. for cpu usage warn on 80% and critical on 90% * critcal value is LOWER than warning value; eg. for free disk space warn on 10% space left and critical on 3% Example: If no warning or critical value is set they are 0 - and a check will return OK on any value. But if they were set then it reacts on these limits. ```shell if [ $iWarnLimit -gt 0 -a $iCriticalLimit -gt 0 ]; then ph.setStatusByLimit $iTotal $iWarnLimit $iCriticalLimit fi ``` ### ph.showtimer Show a time in seconds and milliseconds since start (since source of inc_pluginfunctions.sh). You can use it to show an execution time. Syntax: ```text ph.showtimer ``` It has no parameters. ```shell 2.410 sec ``` ### ph.status Show the current status (set by ``ph.setStatus``) as Text. Syntax: ```text ph.status [TEXT] ``` Parameters: 1. TEXT {string} - optional (but recommended) message to display Without a given text only the status will be shown without linebreak. Example: ```shell if [ $iWarnLimit -gt 0 -a $iCriticalLimit -gt 0 ]; then ph.setStatusByLimit $iTotal $iWarnLimit $iCriticalLimit fi ph.status "NETSTAT - count of connections: $iTotal" ``` This shows OK (or WARNING or CRITICAL) as prefix + ": " + "NETSTAT - count of connections: $iTotal". ``OK: NETSTAT - count of connections: 123`` ### ph.toUnit Transform values eg. to Megabyte or back. The calculation is done by bc. A given Input value will be multiplicated with the source unit and then divided by target unit. It has its limits. Syntax: ```text ph.toUnit VALUE [UNIT] [DIGITS] ``` Parameters: 1. VALUE {integer|float|string} - your input value as integer or float. Behind your value optionally can be a letter for a unit. 2. UNIT {string} - target unit 3. DIGITS {integer} - optional: for return value set a number of digits behind "."; default: no digits (=integer) Valid units are: * "K" - Kilo 2^10 * "M" - Mega 2^20 * "G" - Giga 2^30 * "T" - Tera 2^40 * "P" - Peta 2^50 Examples: ```shell # -- Convert "kilo" into number: ph.toUnit 2K 2048 # -- Convert "kilo" as float value into number: ph.toUnit 2.33K 2385 # -- Get megabytes from a value in bytes: ph.toUnit 314351346 M 29979 # -- Convert an integer source value with Kilo prefix into megabyte and # return as float with 4 digits: ph.toUnit 200.5K M 4 0.1958 ```