In the previous tutorial we have covered the installation and initial setup of MRTG.
In this short one we will add a handful of sensors, OID and script based, before we proceed with the custom sensors for FritzBox in the next tutorial.
Going beyond typical network interface sensors, for which MRTG was developed on the first place, you can add any hardware monitoring sensor that is presented by SNMP service on the target device via a distinct OID.
As a reference, if you check the first sensor, which was automatically added by cfgmaker to the mrtg.cfg file in our previous tutorial, you will see that it is notated as Target[localhost_2]: 2:public@localhost. The number ‘2’ stays here for the second network interface; the first one being usually the loopback.
Customizing sensor presentation
You can customize this sensor to learn a couple of target/sensor specific parameters. Imagine that you’d like to present the output as bits per second, instead. This is the average notation of network bandwidth. Presuming your Raspi eth0 runs at 100Mbit/s, change the MaxBytes value from 125000 to 100000000. Don’t worry, MRTG can handle this value without problems. We’ll come to the limitations of higher than 32-bit integer values in the next tutorial. We also need to adjust the presentation of the values in the Y axis and in the legends. Finally, we need to multiply the output values to 8 to convert from Bytes to bits. All changes marked in red below.
Target[localhost_2]: 2:public@localhost
SetEnv[localhost_2]: MRTG_INT_IP=”192.168.100.12″ MRTG_INT_DESCR=”eth0″
MaxBytes[localhost_2]: 100000000
Factor[localhost_2]: 8
YLegend[localhost_2]: Ethernet Rate
ShortLegend[localhost_2]: bit/s
LegendI[localhost_2]: In:
LegendO[localhost_2]: Out:
Legend1[localhost_2]: Incoming Traffic in bit/s
Legend2[localhost_2]: Outgoing Traffic in bit/s
Title[localhost_2]: Raspi Data Rate eth0
PageTop[localhost_2]: <H1>Raspi Data Rate eth0</H1>
Finally, re-generate the HTML index file to be able to see the new sensor in the MRTG root page:
sudo indexmaker –output=”/var/www/mrtg/index.html” /etc/mrtg.cfg
Note: you will need to repeat this command each time you present new sensor or make changes to existing ones. Also remember to check the log files after such changes, because even if indexmaker does not return any syntax errors there may be internal errors when retrieving the SNMP data. Here’s the command line:
cat /var/log/mrtg/mrtg.log
Addressing explicit OIDs
If we know the specific OIDs for a hardware status, we can configure them as MRTG sensor as long as the output is integer. In the example below, we create a new sensor for CPU utilization.
# Change the MRTG configuration
sudo nano /etc/mrtg.cfg
# Add the below lines exactly as they are (including the three commented lines)
#———————–
# Raspi CPU Load
#———————–
Target[localhost_cpu]: 1.3.6.1.4.1.2021.11.11.0&1.3.6.1.4.1.2021.11.9.0:public@localhost
MaxBytes[localhost_cpu]: 100
Options[localhost_cpu]: integer, gauge, nopercent, unknaszero
YLegend[localhost_cpu]: Idle CPU %
ShortLegend[localhost_cpu]: %
LegendI[localhost_cpu]: Idle:
LegendO[localhost_cpu]: User:
Legend1[localhost_cpu]: Idle CPU time in percentage
Legend2[localhost_cpu]: User CPU time in percentage
Title[localhost_cpu]: Raspi CPU load
PageTop[localhost_cpu]: <H1>Raspi CPU load</H1>
Let’s discuss what we have achieved in this snippet. First, we see that mrtg.cfg file accepts commenting lines, this making our configuration more human readable. Then we add the explicit OIDs, specifically the idle and user CPU times. The MaxBytes parameter is set to 100, obviously, and all the legends are updated accordingly. For the specific meaning of each used parameter, please refer to the MRTG online documentation referenced below.
One important note here: each MRTG sensor expects two, line separated, integer values. This is the essential limitation of MRTG being an In/Out traffic grapher. You cannot have three values in the graph. You can graphically present only one value (using either noi or noo parameters under Options) on the chart, but you cannot configure only one OID, or have a script outputting only one value. This will fill out your mrtg.log with errors and in half of the cases the graphs will either be empty, or you won’t be happy with what you see there. A good way to circumvent this is to have the non-graphed value always returning 0. See Taylor’s comments on the sensor ‘ Raspberry Pi 3 – CPU load ‘ from the first reference below.
Let’s repeat the exercise with a Memory Usage sensor. The lines need to be clear without further comments now. Please note that I prefer to always have two meaningful values instead of one. Matter of taste.
#———————–
# Raspi Memory Usage
#———————–
Target[localhost_mem]: 1.3.6.1.4.1.2021.4.6.0&1.3.6.1.4.1.2021.4.14.0:public@localhost
MaxBytes[localhost_mem]: 439756
Options[localhost_mem]: integer, gauge, nopercent, unknaszero
Factor[localhost_mem]: 1024
YLegend[localhost_mem]: Memory MB
ShortLegend[localhost_mem]: B
LegendI[localhost_mem]: Free:
LegendO[localhost_mem]: Buffered:
Legend1[localhost_mem]: Total RAM free
Legend2[localhost_mem]: Total RAM buffered
Title[localhost_mem]: Raspi Memory Usage
PageTop[localhost_mem]: <H1>Raspi Memory Usage</H1>
Sensors based on script or shell calls
In the next step we will introduce local shell script as output to target and transforming the output.
One very important thing in MRTG sensors is that you can define in the Target keyword a single line of bash shell command instead of network ID or explicit OID. You wrap the command in backticks (`) like the example:
Target[myrouter]: /usr/local/bin/df2mrtg /dev/dsk/c0t2d0s0
Do not use apostrophes (‘) around the command. Also do not use escape () sign within the command line. The MRTG program will read and execute it literary, i.e. in the following example you do not need to escape the && with \&\&
#———————————–
# Raspi CPU temperature
#———————————–
Target[localhost_temp]: cat /sys/class/thermal/thermal_zone0/temp && echo 0
MaxBytes[localhost_temp]: 100000
Options[localhost_temp]: integer, gauge, nopercent, unknaszero, noo
Factor[localhost_temp]: 0.001
YLegend[localhost_temp]: CPU Temperature
ShortLegend[localhost_temp]: °C
LegendI[localhost_temp]: CPU temp
Legend1[localhost_temp]: CPU temperature in °C
Title[localhost_temp]: Raspi CPU temperature
PageTop[localhost_temp]: <H1>Raspi CPU temperature</H1>
The first important difference from the examples in the first reference below (listed in the section "Adding SNMP support for CPU temperature monitoring" there) is that we simplify the process. Instead of creating a shell script, add it with an imaginary OID to the snmpd.conf file and then call it as OID from MRTG, we have only one single line of code and a higher transparency in the mrtg.cfg file.
Secondly, we exemplify a graph with single value in this sensor. Remember, the first value for MRTG means always In, the second (here 0) always the Out. Therefore, we add the ‘noo’ option, meaning No Output to be displayed in the graph. And we define LegendI (I=Input), and Legend1 respectively.
The third important information in this snippet are the Factor and MaxBytes keywords. Because the temperature returned from /sys/class/thermal/thermal_zone0/temp is expressed in millidegrees Celsius (m°C) some conversion is needed. Here we apply the Factor with scale of 0.001. But we nevertheless keep the MaxBytes in the original magnitude, i.e. as the absolute value received and not as the converted one.
This would almost make our sensor perfect if not for one formatting problem. Please observe the following screenshot. The Max, Average and Current values look fine, and the ShortLegend is correct. But the "k" in the Y-axis is not what we want. Strange, but it looks like ‘Factor’ is being applied to the Max/Average/Current presentation only.

A workaround would have been to remove any prepends from the magnitudes. Unfortunately, if we add to the needed sensor configuration with the following line:
kMG[localhost_temp]: ,,
We get rid of "k", but also of "°C"

And we start receiving in /var/log/mrtg/mrtg.log the following:
Use of uninitialized value within @short in pattern match (m//) at /usr/bin/mrtg line 1512.
Use of uninitialized value in sprintf at /usr/bin/mrtg line 1525.
Since debugging 3000 lines of Perl script is not exactly our aim here, we can either ignore the "k" in the Y-axis, or adjust the command line to truncate the last three digits from the output (and then remove the ‘Factor’ line)
cat /sys/class/thermal/thermal_zone0/temp | sed ‘s/…$//’
This proposal is not tested in real life and there may be problems with the apostrophe (‘). In such case you would need to create a shell script as a file and call the file name from the ‘Target’ line in MRTG.
Finally, let’s introduce the last sensor example. This will install a small auxiliary program for pinging remote hosts. Here we again see an execution of shell command within the backticks. The difference from the previous example here is that we are introducing environmental variables during the execution of the code via SetEnv keyword. The other difference is the AbsMax keyword being used here. Normally MRTG ignores values higher than MaxBytes. But if you expect a sort of infrequent "bursts", you can add AbsMax as highest acceptable value.
# Install MRTG ping probe
sudo apt-get install mrtg-ping-probe
# Change the MRTG congifuration
sudo nano /etc/mrtg.cfg
# As usual, add the below lines:
#———————–
# Synology NAS Ping
#———————–
Target[synology_ping]: /usr/bin/mrtg-ping-probe 192.168.100.11
SetEnv[synology_ping]: MRTG_INT_IP=”192.168.100.11″ MRTG_INT_DESCR=”ping”
MaxBytes[synology_ping]: 100
AbsMax[synology_ping]: 200
Options[synology_ping]: gauge, unknaszero
YLegend[synology_ping]: ping time (ms)
ShortLegend[synology_ping]: ms
LegendI[synology_ping]: Max:
LegendO[synology_ping]: Min:
Legend1[synology_ping]: Maximum Round Trip Time in ms
Legend2[synology_ping]: Minimum Round Trip Time in ms
Title[synology_ping]: Synology NAS Ping
PageTop[synology_ping]: <H1>Synology NAS Ping</H1>
With this, we conclude this tutorial. The next, and last, one will lead you through the process of configuring sensors for FritzBox routers.
Reference:
Monitoring The Raspberry Pi with MRTG:
https://www.satsignal.eu/raspberry-pi/monitoring.html
Manpage MRTG-PING-PROBE
https://manpages.debian.org/testing/mrtg-ping-probe/mrtg-ping-probe.1.en.html
MRTG online documentation
https://oss.oetiker.ch/mrtg/doc/mrtg-reference.en.html
Linux SNMP OID’s for CPU, Memory and Disk Statistics
http://www.linux-admins.net/2012/02/linux-snmp-oids-for-cpumemory-and-disk.html