How to Build a Django Server Performance Dashboard for CPU, Memory, and Process Monitoring

This guide walks through creating a Django‑based monitoring system that collects CPU, memory, and process metrics from MySQL, defines models, runs migrations, implements views that format data for Highcharts, builds HTML templates with interactive charts, configures URLs, and runs the server to display real‑time performance dashboards.

Full-Stack DevOps & Kubernetes
Full-Stack DevOps & Kubernetes
Full-Stack DevOps & Kubernetes
How to Build a Django Server Performance Dashboard for CPU, Memory, and Process Monitoring

Monitoring System Overview

The article explains how to build a Django application that monitors server CPU, memory, and process information, stores the data in MySQL, and visualizes it with Highcharts.

1. Environment and Project Structure

Django 2.0.7, Python 3.7, and pymysql 0.9.3 are used. The project follows the standard Django layout with an app named web.

2. Settings Configuration

# Author: Allan
# Datetime: 2019-05-21
import pymysql
pymysql.install_as_MySQLdb()

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.mysql',
        'NAME': 'database',
        'USER': 'username',
        'PASSWORD': 'password',
        'HOST': 'ip',
        'PORT': 3306,
    }
}

INSTALLED_APPS = [
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    'web',
]

MIDDLEWARE = [
    'django.middleware.security.SecurityMiddleware',
    'django.contrib.sessions.middleware.SessionMiddleware',
    'django.middleware.common.CommonMiddleware',
    # 'django.middleware.csrf.CsrfViewMiddleware',  # disabled to avoid 403 errors
    'django.contrib.auth.middleware.AuthenticationMiddleware',
    'django.contrib.messages.middleware.MessageMiddleware',
    'django.middleware.clickjacking.XFrameOptionsMiddleware',
]

ROOT_URLCONF = 'monitor.urls'

TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        'DIRS': [os.path.join(BASE_DIR, 'templates')],
        'APP_DIRS': True,
        'OPTIONS': {
            'context_processors': [
                'django.template.context_processors.debug',
                'django.template.context_processors.request',
                'django.contrib.auth.context_processors.auth',
                'django.contrib.messages.context_processors.messages',
            ],
        },
    },
]

DEBUG = True
ALLOWED_HOSTS = ['*']
LANGUAGE_CODE = 'en-us'
TIME_ZONE = 'Asia/Shanghai'
USE_I18N = True
USE_L10N = True
USE_TZ = False

3. Models for CPU, Memory, and Process Data

from django.db import models

class CpuInfo(models.Model):
    time = models.DateTimeField()
    host = models.CharField(max_length=40)
    usage_system = models.FloatField(null=True)
    usage_user = models.FloatField(null=True)
    usage_softirq = models.FloatField(null=True)
    usage_iowait = models.FloatField(null=True)

class MemoryInfo(models.Model):
    time = models.DateTimeField()
    host = models.CharField(max_length=40)
    used_percent = models.FloatField(null=True)

class ProcstatInfo(models.Model):
    time = models.DateTimeField()
    host = models.CharField(max_length=100)
    exe = models.CharField(max_length=40)
    pid = models.FloatField()
    cpu_usage = models.FloatField(null=True)
    memory_rss = models.FloatField(null=True)

4. Database Migration

# python3 manager.py makemigrations web
# python3 manager.py migrate

5. Views

# Author: Allan
# Datetime: 2019-05-21
import time, json
from django.shortcuts import render
from web import models

def show_procstat(request):
    servers = ['rotestZone01', 'rotestZone02']
    procstat_ret = {}
    for server in servers:
        procstat_info = models.ProcstatInfo.objects.filter(host=server)
        procstat_exe = {}
        for row in procstat_info:
            temp_time = int(time.mktime(row.time.timetuple())) * 1000
            key = f"{row.exe}_{int(row.pid)}"
            if key not in procstat_exe:
                procstat_exe[key] = {'cpu_usage': [], 'memory_rss': []}
            procstat_exe[key]['cpu_usage'].append([temp_time, row.cpu_usage])
            procstat_exe[key]['memory_rss'].append([temp_time, row.memory_rss])
        procstat_ret[server] = procstat_exe
    return render(request, 'show_procstat.html', {"procstat_ret": json.dumps(procstat_ret)})

def show_servers(request):
    servers = ['rotestZone01', 'rotestZone02']
    server_res = {}
    cpu_res = {}
    mem_res = {}
    for server in servers:
        cpu_info = models.CpuInfo.objects.filter(host=server)
        cpu_ret = {'usage_system': [], 'usage_user': [], 'usage_softirq': [], 'usage_iowait': []}
        for row in cpu_info:
            temp_time = int(time.mktime(row.time.timetuple())) * 1000
            cpu_ret['usage_system'].append([temp_time, row.usage_system])
            cpu_ret['usage_user'].append([temp_time, row.usage_user])
            cpu_ret['usage_softirq'].append([temp_time, row.usage_softirq])
            cpu_ret['usage_iowait'].append([temp_time, row.usage_iowait])
        cpu_res[server] = cpu_ret

        mem_info = models.MemoryInfo.objects.filter(host=server)
        mem_ret = []
        for row in mem_info:
            temp_time = int(time.mktime(row.time.timetuple())) * 1000
            mem_ret.append([temp_time, row.used_percent])
        mem_res[server] = mem_ret

    server_res['cpu_res'] = cpu_res
    server_res['mem_res'] = mem_res
    return render(request, 'show_servers.html', {"server_res": json.dumps(server_res)})

6. HTML Templates

<html>
<head>
    <meta charset="UTF-8"/>
    <title>Server Monitoring</title>
    <script src="https://code.jquery.com/jquery-3.1.1.min.js"></script>
    <script src="https://code.highcharts.com/highcharts.js"></script>
    <script src="https://code.highcharts.com/modules/exporting.js"></script>
    <script src="https://code.highcharts.com/modules/export-data.js"></script>
    <script>
    $(document).ready(function () {
        $("#servers").change(function () {
            var selected = $(this).children('option:selected').val();
            var server_res = jQuery.parseJSON('{{ server_res|safe }}');
            var cpu_res = server_res['cpu_res'];
            var cpu_info = cpu_res[selected];
            Highcharts.setOptions({global:{useUTC:false}});
            Highcharts.chart('cpu', {
                chart:{zoomType:'x'},
                title:{text:selected + ': CPU 信息'},
                xAxis:{type:'datetime'},
                yAxis:{title:{text:'使用率 (%)'}},
                legend:{enabled:false},
                plotOptions:{area:{fillColor:{linearGradient:{x1:0,y1:0,x2:0,y2:1},stops:[[0,Highcharts.getOptions().colors[0]],[1,Highcharts.Color(Highcharts.getOptions().colors[0]).setOpacity(0).get('rgba')]]},marker:{radius:2},lineWidth:1,threshold:null}},
                series:[
                    {type:'area',name:'usage_system',data:cpu_info['usage_system']},
                    {type:'area',name:'usage_user',data:cpu_info['usage_user']},
                    {type:'area',name:'usage_softirq',data:cpu_info['usage_softirq']},
                    {type:'area',name:'usage_iowait',data:cpu_info['usage_iowait']}
                ]
            });
            var mem_res = server_res['mem_res'];
            var mem_info = mem_res[selected];
            Highcharts.chart('mem', {
                chart:{zoomType:'x'},
                title:{text:selected + ': 内存信息'},
                xAxis:{type:'datetime'},
                yAxis:{title:{text:'使用率 (%)'}},
                legend:{enabled:false},
                plotOptions:{area:{fillColor:{linearGradient:{x1:0,y1:0,x2:0,y2:1},stops:[[0,Highcharts.getOptions().colors[0]],[1,Highcharts.Color(Highcharts.getOptions().colors[0]).setOpacity(0).get('rgba')]]},marker:{radius:2},lineWidth:1,threshold:null}},
                series:[{type:'area',name:'used_percent',data:mem_info}]
            });
        });
    });
    </script>
</head>
<body>
    <div><h2>服务器监控信息</h2></div>
    <select id="servers">
        <option value="servers">请选择要监控的服务器</option>
        <option value="rotestZone01">rotestZone01</option>
        <option value="rotestZone02">rotestZone02</option>
    </select>
    <div id="cpu" style="width:1560px;height:400px;margin:0 auto"></div>
    <div id="mem" style="width:1560px;height:400px;margin:0 auto"></div>
</body>
</html>

7. URL Routing

# Author: Allan
# Datetime: 2019-05-21
from django.contrib import admin
from django.urls import path
from web import views

urlpatterns = [
    # path('admin/', admin.site.urls),
    path('show_servers', views.show_servers),
    path('show_procstat', views.show_procstat),
]

8. Running the Application

# python3 manager.py runserver

After launching the server, open the URLs in a browser; the page displays interactive Highcharts graphs for CPU usage, memory usage, and per‑process statistics.

CPU and memory chart
CPU and memory chart
Process information chart
Process information chart
Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

BackendDjangohighcharts
Full-Stack DevOps & Kubernetes
Written by

Full-Stack DevOps & Kubernetes

Focused on sharing DevOps, Kubernetes, Linux, Docker, Istio, microservices, Spring Cloud, Python, Go, databases, Nginx, Tomcat, cloud computing, and related technologies.

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.