rrd-beginners (1)
Leading comments
Automatically generated by Pod::Man 4.09 (Pod::Simple 3.35) Standard preamble: ========================================================================
NAME
rrd-beginners - RRDtool Beginners' GuideSYNOPSIS
Helping new RRDtool users to understand the basics of RRDtoolDESCRIPTION
This manual is an attempt to assist beginners in understanding the concepts of RRDtool. It sheds a light on differences between RRDtool and other databases. With help of an example, it explains the structure of RRDtool database. This is followed by an overview of the ``graph'' feature of RRDtool. At the end, it has sample scripts that illustrate the usage/wrapping of RRDtool within Shell or Perl scripts.What makes RRDtool so special?
RRDtool is- *
- RRDtool stores data; that makes it a back-end tool. The RRDtool command set allows one to create graphs; that makes it a front-end tool as well. Other databases just store data and can not create graphs.
- *
- In case of linear databases, new data gets appended at the bottom of the database table. Thus its size keeps on increasing, whereas the size of an RRDtool database is determined at creation time. Imagine an RRDtool database as the perimeter of a circle. Data is added along the perimeter. When new data reaches the starting point, it overwrites existing data. This way, the size of an RRDtool database always remains constant. The name ``Round Robin'' stems from this behavior.
- *
- Other databases store the values as supplied. RRDtool can be configured to calculate the rate of change from the previous to the current value and store this information instead.
- *
-
Other databases get updated when values are supplied. The RRDtool database
is structured in such a way that it needs data at predefined time
intervals. If it does not get a new value during the interval, it stores an
UNKNOWNvalue for that interval. So, when using the RRDtool database, it is imperative to use scripts that run at regular intervals to ensure a constant data flow to update the RRDtool database.
RRDtool is designed to store time series of data. With every data update, an associated time stamp is stored. Time is always expressed in seconds passed since epoch (01-01-1970). RRDtool can be installed on Unix as well as Windows. It comes with a command set to carry out various operations on
Understanding by an example
The structure of anThe structure of a database and the terminology associated with it can be best explained with an example.
rrdtool create target.rrd \ --start 1023654125 \ --step 300 \ DS:mem:GAUGE:600:0:671744 \ RRA:AVERAGE:0.5:12:24 \ RRA:AVERAGE:0.5:288:31
This example creates a database named target.rrd. Start time (1'023'654'125) is specified in total number of seconds since epoch (time in seconds since 01-01-1970). While updating the database, the update time is also specified. This update time
The step of 300 seconds indicates that the database expects new values every 300 seconds. The wrapper script should be scheduled to run every step seconds so that it updates the database every step seconds.
DS:variable_name:DST:heartbeat:min:max
Note, that if you do
Values = 300, 600, 900, 1200 Step = 300 seconds COUNTER DS = 1, 1, 1, 1 DERIVE DS = 1, 1, 1, 1 ABSOLUTE DS = 1, 2, 3, 4 GAUGE DS = 300, 600, 900, 1200
The next parameter is heartbeat. In our example, heartbeat is 600 seconds. If the database does not get a new
The next two parameters are the minimum and maximum value, respectively. If the variable to be stored has predictable maximum and minimum values, this should be specified here. Any update value falling out of this range will be stored as
The next line declares a round robin archive (
RRA:CF:xff:step:rows
Lets have a look at the example above. For the first
Graphical Magic
Another important feature of RRDtool is its ability to create graphs. The ``graph'' command uses the ``fetch'' command internally to retrieve values from the database. With the retrieved values it draws graphs as defined by the parameters supplied on the command line. A single graph can show differentValues of different variables can be presented in 5 different shapes in a graph -
Wrapping RRDtool within Shell/Perl script
After understanding RRDtool it is now a time to actually use RRDtool in scripts. Tasks involved in network management are data collection, data storage, and data retrieval. In the following example, the previously created target.rrd database is used. Data collection and data storage is done using Shell scripts. Data retrieval and report generation is done using Perl scripts. These scripts are shown below:Shell script (collects data, updates database)
#!/bin/sh a=0 while [ "$a" == 0 ]; do snmpwalk -c public 192.168.1.250 hrSWRunPerfMem > snmp_reply total_mem=`awk 'BEGIN {tot_mem=0} { if ($NF == "KBytes") {tot_mem=tot_mem+$(NF-1)} } END {print tot_mem}' snmp_reply` # I can use N as a replacement for the current time rrdtool update target.rrd N:$total_mem # sleep until the next 300 seconds are full perl -e 'sleep 300 - time % 300' done # end of while loop
Perl script (retrieves data from database and generates graphs and statistics)
#!/usr/bin/perl -w # This script fetches data from target.rrd, creates a graph of memory # consumption on the target (Dual P3 Processor 1 GHz, 656 MB RAM) # call the RRD perl module use lib qw( /usr/local/rrdtool-1.0.41/lib/perl ../lib/perl ); use RRDs; my $cur_time = time(); # set current time my $end_time = $cur_time - 86400; # set end time to 24 hours ago my $start_time = $end_time - 2592000; # set start 30 days in the past # fetch average values from the RRD database between start and end time my ($start,$step,$ds_names,$data) = RRDs::fetch("target.rrd", "AVERAGE", "-r", "600", "-s", "$start_time", "-e", "$end_time"); # save fetched values in a 2-dimensional array my $rows = 0; my $columns = 0; my $time_variable = $start; foreach $line (@$data) { $vals[$rows][$columns] = $time_variable; $time_variable = $time_variable + $step; foreach $val (@$line) { $vals[$rows][++$columns] = $val;} $rows++; $columns = 0; } my $tot_time = 0; my $count = 0; # save the values from the 2-dimensional into a 1-dimensional array for $i ( 0 .. $#vals ) { $tot_mem[$count] = $vals[$i][1]; $count++; } my $tot_mem_sum = 0; # calculate the total of all values for $i ( 0 .. ($count-1) ) { $tot_mem_sum = $tot_mem_sum + $tot_mem[$i]; } # calculate the average of the array my $tot_mem_ave = $tot_mem_sum/($count); # create the graph RRDs::graph ("/images/mem_$count.png", "--title= Memory Usage", "--vertical-label=Memory Consumption (MB)", "--start=$start_time", "--end=$end_time", "--color=BACK#CCCCCC", "--color=CANVAS#CCFFFF", "--color=SHADEB#9999CC", "--height=125", "--upper-limit=656", "--lower-limit=0", "--rigid", "--base=1024", "DEF:tot_mem=target.rrd:mem:AVERAGE", "CDEF:tot_mem_cor=tot_mem,0,671744,LIMIT,UN,0,tot_mem,IF,1024,/", "CDEF:machine_mem=tot_mem,656,+,tot_mem,-", "COMMENT:Memory Consumption between $start_time", "COMMENT: and $end_time ", "HRULE:656#000000:Maximum Available Memory - 656 MB", "AREA:machine_mem#CCFFFF:Memory Unused", "AREA:tot_mem_cor#6699CC:Total memory consumed in MB"); my $err=RRDs::error; if ($err) {print "problem generating the graph: $err\n";} # print the output print "Average memory consumption is "; printf "%5.2f",$tot_mem_ave/1024; print " MB. Graphical representation can be found at /images/mem_$count.png.";