DD-WRT Network Stats Graphics using Grafana and InfluxDB

Dashboard

Do you have a DD-WRT enabled router and want network statistics graphics for all the devices at your home or office? It’s pretty easy with InfluxDB and Grafana!

Installing InfluxDB

InfluxDB is a time series database. This means it is specialized in collecting, storing and querying sequences of measurements over a time interval. It is great doing this job, and since it’s exactly the job that we need, we’re going to use it.

As always the steps on this article are for Debian-based Linux distributions. Just issue these commands:

If you prefer to add a PPA to your repository list, follow these instructions instead.

If everything went fine then we can login through the console like this:

Or we could log in through the GUI at http://localhost:8083

Configuring InfluxDB

We need to configure the database for our network traffic data. Let’s just create a new database called traffic. You can do it through the console or through the Web GUI:

Collecting Data

Now we need to populate the database with time based data.

First we need to create a script that will run in the DD-WRT enabled router that will let us gather statistics from every device in the same LAN the router is. The idea is that per every device in your LAN the script will create two entries in a new chain in the enabled router’s iptables, one for incoming packets, and another one for outgoing packets, both with target RETURN, so it returns to the original chain. Then in the FORWARD chain we are going to send to the RRDIPT chain every single packet there, the RRDIPT chain will count the packet, and then will return to the FORWARD chain.

The FORWARD chain will have an entry like this:

And the RRDIPT chain will have an entry per every device like this:

You can find my complete script here. By the way this was not my idea. This is all based in a script called wrtbwmon.

This script has to run every minute in the router’s cron to gather statistics and every hour or so to detect new devices in your LAN. Also remember to change the DBURL environment variable with the URL of your InfluxDB database in your LAN.

To do this you have a couple of choices depending on if you can enable JFFS or not in your router.

JFFS Capable Router

If your router has enough memory then you can enable JFFS. Follow the instruction on how to enable JFFS in your DD-WRT enabled router first and copy the script in /jffs/bin and name it trafficmon (no extension). Remember to give the script execution permissions (chmod +x trafficmon).

Now you have to enable cron in the Administration tab of your router and paste the following lines in the Additional Cron Jobs field:

If you want to be more elegant, create instead a startup script in /jffs/etc/config to include the cron lines you need every time you restart your router:

Don’ t forget to give execution permission to the startup script (chmod +x trafficmon.startup).

No JFFS Available

If your router has no enough memory and you don’t have or can’t create a JFFS partition, then you need a web server in your LAN to host the script. Enable cron in the Administration tab of your router and paste the following lines in the Additional Cron Jobs field. Remember to edit them to point to your web server since in the following example we’re assuming the script is hosted at http://192.168.100.100/trafficmon

Checking Work So Far

If you have left your router doing its job for more than a minute then you should already have data in your InfluxDB. You can query the data using the InfluxDB’s Web Interface at port 8083 in your server (remember to choose the database first before querying the data):

InfluxDB

Everything looks great! Now we just need to create graphs for this data.

Installing Grafana

Grafana is the software that generates graphics for several time series databases, including of course InfluxDB. Just issue the following commands to install it:

If everything went well you can login at http://localhost:3000. The default login and password are admin.

Configure the Data Source

Let’s configure our InfluxDB as a data source in Grafana. Go to Data Sources and click on New. Fill the form with a name for your InfluxDB database (I used “InfluxDB”) and select InfluxDB as Type. If Grafana and InfluxDB are running in the same server, the URL should be http://localhost:8086. We named our InfluxDB database “traffic” and just type anything in the user and password fields. Those are not used but if they are empty Grafana won’t let you go on.

It should look like this:

Grafana4

Click on Add and we are ready to create some graphs.

Create Some Graphs

Create a new Dashboard clicking on Home and then New and then add a new graph clicking in the green icon at your left (that’s the menu of the row) and then on Add Panel and then Graph.

Select InfluxDB as your query type and then add two queries (one for the downstream and another one for the upstream of the host you want to create the graph for).

Now define the queries like this in the Metrics tab:

Grafana

As you can see since we are collecting data every minute but we want to show bytes per second, we have to divide the average (the mean) by 60.

You can define some nifty legends and stuff in the Axis & Grid tab:

Grafana2

And the graph should look like this:

Grafana3

Do this for every device in your home or office and that’s it! If you want a graph with all the traffic select the MAC address 00:00:00:00:00:00.

10 thoughts on “DD-WRT Network Stats Graphics using Grafana and InfluxDB

  1. I followed your guide to the letter, and I am getting stats on the 00:00 MAC address, so I know the script and cron are working on my router(R7000). However I’m not getting any network stats for all the other MAC addresses of my various devices. They all show as 0 in InfluxDB. Can you provide any insight? Thanks!

    • Sounds like the “setup” command is not running properly. That’s the one that looks for all the active IP addresses in your network and create separate rules for them. Remember the cron file has two entries:

      * * * * * root /jffs/bin/trafficmon update
      0 * * * * root /jffs/bin/trafficmon setup

      You can also try to run the command manually in your router (/jffs/bin/traficmon/setup) to recreate the individual hosts rules.

    • Same here – getting all traffic on 00:00. Also using an R7000.

      Tried running setup script both with cron and manually to no avail. I /am/ able to see individual MAC addresses in InfluxDB, but everything besides 00:00 has a zero value.

      • If you type in your router:

        iptables -L RRDIPT -n -v

        Are you able to see all the IP addresses in your network with meaningful values on pkts and bytes columns?

  2. If you are seeing RRDIPT empty change this line (line #79) in the trafficmon script (I’m updating the link as well):

    iptables -L FORWARD –line-numbers -n | grep “RRDIPT” | grep “1” > /dev/null

    to:

    iptables -L FORWARD -n | grep RRDIPT[^2] > /dev/null

    Or just replace the script with the new one in the link.

  3. What is MAC address 00:00:00:00:00:00?

    It seems to be working on all the other MAC addresses on my network but then i get random data on 00. I thought this would be the total but its way less then my top user. My top user had 40gb yesterday and 00 had 2.8.

    • It is the total.

      Check that the very first two rules on the FORWARD chain of iptables are your RRDIPT rules like this:

      root@DD-WRT:~# iptables -L FORWARD -n -v
      Chain FORWARD (policy ACCEPT 0 packets, 0 bytes)
      pkts bytes target prot opt in out source destination
      86 8046 RRDIPT 0 — * * 0.0.0.0/0 0.0.0.0/0
      86 8046 RRDIPT2 0 — * * 0.0.0.0/0 0.0.0.0/0

      Also, RRDIPT2 checks for from br0 to eth1 and from eth1 to br0. Maybe your router is different?

      root@DD-WRT:~# iptables -L RRDIPT2 -n -v
      Chain RRDIPT2 (1 references)
      pkts bytes target prot opt in out source destination
      62 4717 RETURN 0 — br0 eth1 0.0.0.0/0 0.0.0.0/0
      67 5901 RETURN 0 — eth1 br0 0.0.0.0/0 0.0.0.0/0

      Check what are the interfaces for LAN and for WAN in your router. In my case (and the case of the script) eth1 is WAN (it has the WAN IP address assigned) and br0 is LAN (it has the LAN IP address). Maybe you have a different router where DD-WRT assigns different interfaces for WAN and LAN.

      • Actually the script is smart enough to know your interfaces:

        LAN_IFNAME=$(nvram get lan_ifname)
        WAN_IFNAME=$(nvram get wan_ifname)

        But you should double check they are the correct interfaces.

        • Ya i see now that 00:00:: is inverted.

          The issue i am now having is that I have 3 LAN interfaces Its working for my wired but not counting for wireless. I have eth0, ATH0, and ATH1 on my LAN. eth1 is my WAN.

Leave a Reply