Herramientas de usuario

Herramientas del sitio


tutoriales:rrdtool

Graficar tráfico del enlace con RRDTool

Este tutorial puede tener muchos aspectos sin pulir, porque es la primera vez que utilizo esta herramienta. Mi acercamiento fue motivado por el deseo de tener una solución rápida y de bajo consumo de recursos que me permitiera muestrear y graficar la transferencia del enlace de mi trabajo en intervalos de tiempo inferiores a los 5 minutos que suele utilizar MRTG.

Introducción a RRDTool

RRDTool es una aplicación desarrollada por Tobias Oetiker (creador del popular MRTG) específicamente para registrar y graficar series de datos basados en el tiempo.

Esta herramienta ofrece mayor flexibilidad para graficar que MRTG y también mejor rendimiento, pues los gráficos se generan solo bajo demanda, de modo que la única carga para el sistema es el registro de los datos, que tiene muy bajo consumo de recursos.

Los datos se almacenan en una base de datos RRD (round robin database), que mantiene un tamaño constante y permite registrar diferentes intervalos de tiempo.

Aunque RRDTool puede utilizarse para muchas cosas, en este tutorial explicaremos cómo utilizarlo para llevar un registro histórico de la transferencia de un enlace.

Algunas cosas que se asumen en este tutorial:

  • Poseemos un nivel intermedio de familiaridad con Linux (con todo lo que ello implica).
  • Tenemos un enrutador que ya está configurado para enviar información mediante el protocolo SNMP, que tiene la dirección IP 192.168.1.1 y cuya cadena de comunidad es MiComunidad.
  • El enlace que deseamos monitorear permite una transferencia sostenida de 128 kbps con picos que en ningún caso excederán los 160 kpbs.
  • El servidor que utilizaremos para almacenar los datos tiene la dirección 192.168.1.2 y utiliza Debian Squeeze como sistema operativo.
  • Deseamos mantener un registro histórico por un periodo de un año, con tres resoluciones de tiempo diferentes.

Instalación y configuración

Además de necesitar instalar RRDTool, para comunicarnos con el enrutador mediante SNMP necesitaremos tener instalados varios paquetes, pero podemos instalarlos todos de una vez:

sudo aptitude install snmp smistrip snmp-mibs-downloader rrdtool

Una aclaración:

A partir de Debian Squeeze los archivos MIB ya no pertenecen al paquete libsnmp-base, sino que por un cambio en su licencia se movieron a la sección de componentes non-free, de modo que para evitar errores en algunos comandos, conviene instalar el paquete snmp-mibs-downloader, al menos temporalmente. También debemos colocar una marca de comentario en el archivo /etc/snmp/snmp.conf, de modo que quedaría así:

#mibs :

Creación de la base de datos

El primer paso para utilizar RRDTool es crear la base de datos. Pueden utilizarse diferentes parámetros, sobre los cuales podremos conocer más con el comando man rrdcreate. No obstante, para abreviar, utilizaremos un simple script de bash:

creardatos.sh
#! /bin/sh
# Script para crear base de datos RRD para monitoreo de enlace
 
# Directorio de la base de datos
RRDATADIR=/var/log/rrd
 
# Archivo de la base de datos
RRDATAFILE=enrutador.rrd
 
# Crear directorio si no existe
mkdir -p $RRDATADIR
 
# Crear base de datos, si no existe
if [ ! -f "$RRDATADIR/$RRDATAFILE" ]; then
  sudo rrdtool create "$RRDATADIR/$RRDATAFILE" \
  --step 10 \
  DS:in:COUNTER:20:0:20000 \
  DS:out:COUNTER:20:0:20000 \
  RRA:AVERAGE:0.5:3:8640 \
  RRA:AVERAGE:0.5:30:25920 \
  RRA:AVERAGE:0.5:720:4380
fi
 
exit 0

El significado de este script básicamente es el siguiente:

  • Las muestras se recibirán cada 10 segundos (la base de datos se encarga de promediarlas).
  • Se crearán dos orígenes de datos (uno para la entrada y otro para la salida) en los cuales se registrarán valores entre 0 y 20000 bytes por segundo, es decir, 16000 bytes (128 kilobits) mas un margen de 4000 bytes (32 kilobits, el 25%) para posbibles picos.
  • Se almacenarán por por 72 horas los valores promediados de 30 segundos (para poder conocer con mayor detalle el comportamiento reciente del enlace).
  • Se almacenarán por 90 días los valores promediados de 5 minutos.
  • Se almacenarán por un año los valores promediados de 2 horas.

Consultar el dispositivo

Para consultar el enrutador utilizaremos el protocolo SNMP. Hay muchas herramientas que lo soportan, pero en este tutorial haremos el proceso manualmente.

Primeramente, necesitamos saber cuál es la interfaz del enrutador que deseamos monitorear, y para esto podemos utilizar el siguiente comando:

snmpwalk -v1 -c MiComunidad 192.168.1.1 interfaces.ifTable.ifEntry.ifDescr

Este comando debería producir un listado de interfaces, parecido a este:

IF-MIB::ifDescr.10000 = STRING: eth-0
IF-MIB::ifDescr.40000 = STRING: dsl-0
IF-MIB::ifDescr.140000 = STRING: atm-0
IF-MIB::ifDescr.150000 = STRING: aal5-0
IF-MIB::ifDescr.150001 = STRING: aal5-1
IF-MIB::ifDescr.150002 = STRING: aal5-2
IF-MIB::ifDescr.150003 = STRING: aal5-3
IF-MIB::ifDescr.150004 = STRING: aal5-4
IF-MIB::ifDescr.150005 = STRING: aal5-5
IF-MIB::ifDescr.150006 = STRING: aal5-7
IF-MIB::ifDescr.150007 = STRING: aal5-6

En este caso, nos interesa la interfaz dsl-0, de modo que apuntamos su número (4000). Una vez hecho esto, buscamos las entradas MIB ifInOctets y ifOutOctets, que son las que devuelven los valores de los bytes recibidos y enviados. Hay varias formas de encontrarlas, pero la mejor manera (para el sistema) es por su valor numérico, de modo que utilizaremos los siguientes comandos:

snmptranslate -Tz | grep ifInOctets
snmptranslate -Tz | grep ifOutOctets

Deberíamos obtener valores como estos:

1.3.6.1.2.1.2.2.1.10
1.3.6.1.2.1.2.2.1.16

Si deseamos conocer el significado de esta secuencia de números, podemos utilizar el siguiente comando:

snmptranslate -Onf -IR ifInOctets

Obtendremos algo como esto:

.org.dod.internet.mgmt.mib-2.interfaces.ifTable.ifEntry.ifInOctets

De todas maneras, consultaremos ahora el enrutador con la secuencia de números que obtuvimos, y al final agregaremos el número de la interfaz que obtuvimos anteriormente (4000):

snmpget -v1 -c MiComunidad 192.168.1.1 .1.3.6.1.2.1.2.2.1.10.40000 .1.3.6.1.2.1.2.2.1.16.40000

Deberíamos obtener algo como esto:

IF-MIB::ifInOctets.40000 = Counter32: 78906432
IF-MIB::ifOutOctets.40000 = Counter32: 26193216

Esto significa que el enrutador está respondiendo con los valores que tienen los contadores, que son los que necesitaremos para poblar la base de datos.

Registrar los datos

Como mencionamos anteriormente, para poblar la base de datos, utilizaremos un script de bash, que consulte al enrutador y envíe los valores obtenidos a la base de datos. Como la consulta debe hacerse cada diez segundos, a mi se me ocurrió algo simple como esto:1)

enrutador.sh
#! /bin/sh
 
REPEAT=1
RRDATAFILE=/var/log/rrd/enrutador.rrd
 
while [ "$REPEAT" -eq 1 ]; do
  BYTESIN=$(snmpget -v1 -c MiComunidad 192.168.1.1 .1.3.6.1.2.1.2.2.1.10.40000 | awk '{print $4}')
  BYTESOUT=$(snmpget -v1 -c MiComunidad 192.168.1.1 .1.3.6.1.2.1.2.2.1.16.40000 | awk '{print $4}')
  rrdtool update $RRDATAFILE N:$BYTESIN:$BYTESOUT
  sleep 10
done

Como vemos, en este caso, utilizamos el comando snmpget en un ciclo que se repite mientras se ejecute el script, extraemos solo las cifras de los contadores mediante el comando AWK, las asignamos a variables, y luego las pasamos a la base de datos mediante el comando rrdtool update (aquí N significa la hora actual). Al final se hace una pausa de 10 segundos.

Podría utilizarse otra variante sin ciclo y simplemente llamar el script desde una tarea programada, pero crontab tiene un límite inferior de un minuto.

De modo que como no utilizaremos crontab, queda decidir desde dónde llamaremos al script. Tiene sentido que se consulte al enrutador en cuanto el servidor levante las interfaces de red, asi que por ejemplo, podríamos colocar el script (que por cierto, debe tener permisos de ejecución) en /etc/network/if-up.d/ o también puede agregarse esta línea al archivo /etc/network/interfaces:

up /etc/network/enrutador.sh &

Una vez terminado este paso, podemos reiniciar la red o la interfaz, o simplemente llamar el script manualmente para que comience a llenar la base de datos. En todo caso, debemos esperar algunos minutos antes de hacer nuestra primera graficación, porque de lo contrario solo veremos unas barras enormes.

Graficar

Evidentemente, la parte más interesante y creativa es la graficación. Con RRDTool pueden hacerse gráficos realmente complejos, pues las versiones recientes soportan incluso niveles de transparencia.


(Pretendo terminar esta sección pronto, pero para los impacientes, aqui va un script que ejemplifica como utilizar el comando de graficación.)

graficar.sh
#! /bin/sh
 
RRDATAFILE=/var/log/rrd/enrutador.rrd
 
if [ $# -lt 2 ]; then
  echo "Faltan los momentos de inicio y fin. Ej. (end-6h now)"
  exit 0
else
  sudo rrdtool graph /var/www/rrd/rrdtool_ejemplo.png --imgformat PNG \
  --start $1 --end $2 \
  --title "Comportamiento del enlace" \
  --vertical-label "Tasa de transferencia (kbps)" \
  --upper-limit 160 \
  --lower-limit 0 \
  --rigid \
  --width 600 --height 240 \
  DEF:dsin=$RRDATAFILE:in:AVERAGE \
  DEF:dsout=$RRDATAFILE:out:AVERAGE \
  CDEF:download=dsin,0.008,* \
  CDEF:down96=download,96,GT,0,download,IF \
  CDEF:down64=download,64,GT,0,download,IF \
  CDEF:down32=download,32,GT,0,download,IF \
  CDEF:down13=download,13,GT,0,download,IF \
  CDEF:upload=dsout,0.008,* \
  HRULE:128#0000FF:"Capacidad contratada (128 kbps)\n" \
  AREA:download#35DF7F:"Recepción superior al 75%\n" \
  AREA:down96#AFDF3F:"Recepción inferior al 75% (96 kbps)\n" \
  AREA:down64#EFDF1F:"Recepción inferior al 50% (64 kbps)\n" \
  AREA:down32#FF9F00:"Recepción inferior al 25% (32 kbps)\n" \
  AREA:down13#FF0000:"Recepción inferior al 10% (13 kbps)\n" \
  LINE1:download#006000 \
  LINE1.5:upload#005FBF:"Envío"
fi
 
exit 0

El primer parámetro que espera recibir el script es el timestamp de inicio y el segundo es el timestamp final, donde cada timestamp es la cantidad de segundos transcurridos desde 1970-01-01 00:00:00 UTC.

Afortunadamente, Oetiker también implementó abreviaturas al estilo de horario del comando at:

Abreviatura Significado
now El momento actual
s Segundos
h Horas
d Días
w Semanas
m Meses
y Años
start Referencia al momento inicial
end Referencia al momento final
midnight 00:00
noon 12:00
teatime 16:00
yesterday Referencia al día anterior
today Referencia al día actual
tomorrow Referencia al día próximo
epoch 1970-01-01 00:00:00 UTC

Además puede utilizarse la hora (en formato de 24 horas), el nombre de los días (en inglés) o la fecha en alguno de estos formatos:

  • MM/DD/[YY]YY
  • DD.MM.[YY]YY
  • YYYYMMDD

Esto facilita la invocación de nuestro script, por ejemplo, para obtener la última hora:

./graficar.sh now-1h now

Resultados

Con RRDTool se pueden obtener resultados visualmente superiores a los que brinda MRTG, aqui tienen un ejemplo del gráfico generado con el script anterior:

Atribuciones

  • Autor: Hugo Florentino
1)
Es probable que puedan encontrarse soluciones más eficientes (como crear un daemon), pero esta al menos funciona y se prepara rápido.
tutoriales/rrdtool.txt · Última modificación: 2020/04/22 20:57 (editor externo)