Skip to main content

Ops Monitoring Dashboards with Vizly

You monitor servers, APIs, and infrastructure. You have Prometheus metrics, CloudWatch datapoints, or Elasticsearch logs. Vizly gives you ops-themed chart presets and metric normalization helpers so you can go from raw observability JSON to a dashboard in a few lines.

Prometheus metrics to charts

Vizly normalizes Prometheus API JSON into a DataFrame, then you chart it directly.

import vizly as vz

# Normalize Prometheus response (you already have the JSON)
prometheus_data = {
"status": "success",
"data": {
"result": [
{"metric": {"__name__": "http_requests_total", "instance": "web-1"},
"values": [[1719792000, "120"], [1719795600, "145"]]},
{"metric": {"__name__": "http_requests_total", "instance": "web-2"},
"values": [[1719792000, "98"], [1719795600, "112"]]},
]
}
}

df = vz.from_prometheus(prometheus_data)
# Returns DataFrame with columns: timestamp, value, series

vz.set_theme("ops_grafana")
chart = vz.line(df, x="timestamp", y="value", title="HTTP Requests")
chart.to_html()

System metrics dashboard

A single-page ops dashboard with CPU, memory, disk, and request rate.

import pandas as pd
import vizly as vz

vz.set_theme("ops_cloudwatch")

# System metrics data
df_cpu = pd.DataFrame({
'time': pd.date_range('2026-07-28 00:00', periods=24, freq='1h'),
'cpu_user': [34, 31, 29, 28, 32, 38, 45, 52, 61, 68, 72, 71,
65, 62, 58, 55, 51, 48, 46, 44, 42, 39, 37, 35],
'cpu_system': [12, 11, 10, 9, 11, 14, 17, 21, 26, 30, 33, 31,
28, 25, 22, 20, 18, 16, 15, 14, 13, 12, 11, 10],
})

df_memory = pd.DataFrame({
'time': pd.date_range('2026-07-28 00:00', periods=24, freq='1h'),
'used_gb': [14, 13, 13, 12, 13, 15, 18, 22, 26, 28, 30, 29,
27, 25, 23, 21, 19, 18, 17, 16, 16, 15, 14, 14],
'cached_gb': [8, 8, 7, 7, 8, 9, 10, 11, 12, 13, 13, 12,
11, 10, 10, 9, 9, 8, 8, 7, 7, 7, 6, 6],
})

df_requests = pd.DataFrame({
'time': pd.date_range('2026-07-28 00:00', periods=24, freq='1h'),
'requests': [1200, 980, 850, 720, 1100, 2100, 4500, 8200, 12100,
15800, 16200, 15100, 13200, 11800, 10500, 9500,
8700, 7800, 6900, 6100, 5500, 4800, 3200, 1800],
'errors': [2, 1, 0, 1, 3, 5, 12, 18, 24, 22, 19, 15,
13, 10, 8, 7, 6, 5, 4, 4, 3, 2, 2, 1],
})

# Build the ops dashboard
chart = vz.page(charts=[
vz.area(df_cpu, x='time', y=['cpu_user', 'cpu_system'],
title='CPU Usage (%)'),
vz.area(df_memory, x='time', y=['used_gb', 'cached_gb'],
title='Memory Usage (GB)'),
vz.line(df_requests, x='time', y=['requests', 'errors'],
title='Request Rate & Errors'),
vz.gauge(value=72, title='Current CPU'),
], title="System Ops Dashboard")
chart.to_html()

CloudWatch integration

import vizly as vz

# Normalize CloudWatch GetMetricStatistics response
cw_data = {
"Label": "CPUUtilization",
"Datapoints": [
{"Timestamp": "2026-07-28T00:00:00Z", "Average": 42.5, "Unit": "Percent"},
{"Timestamp": "2026-07-28T01:00:00Z", "Average": 38.2, "Unit": "Percent"},
]
}

df = vz.from_cloudwatch(cw_data)
vz.set_theme("ops_cloudwatch")
chart = vz.line(df, x="timestamp", y="value", title="EC2 CPU Utilization")

Elasticsearch log monitoring

import vizly as vz

# Normalize Elasticsearch search response
es_data = {
"hits": {
"hits": [
{"_source": {"@timestamp": "2026-07-28T00:00:00Z", "response_time": 145}},
{"_source": {"@timestamp": "2026-07-28T00:01:00Z", "response_time": 203}},
]
}
}

df = vz.from_elasticsearch(es_data)
# v1.0.1 also provides from_elk as a shorter alias
df = vz.from_elk(es_data)
vz.set_theme("ops_kibana")
chart = vz.line(df, x="timestamp", y="value", title="API Response Time (ms)")

Data quality note

Data ingest loaders (from_prometheus, from_cloudwatch, from_elasticsearch, from_elk) drop rows with missing or unparseable timestamps/values. Check the vizly_skipped attribute on the returned object to inspect skipped rows:

result = vz.from_prometheus(raw_data)
df = result["data"] # clean rows
skipped = result.vizly_skipped # list of dicts: [{row, reason}]

Heatmap for traffic patterns

Visualize request volume by day/hour to find peak traffic windows.

import pandas as pd
import vizly as vz

# Weekly activity data
data = []
days = ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun']
hours = ['9am', '12pm', '3pm', '6pm', '9pm']
for day in days:
for hour in hours:
data.append({'day': day, 'hour': hour, 'requests':
hash((day, hour)) % 81 + 20})

df = pd.DataFrame(data)
chart = vz.heatmap(df, x='day', y='hour', values='requests',
title='Request volume by day/hour', theme='ops_grafana')

Gauge cluster

Show multiple KPIs as gauges for a at-a-glance status view.

import vizly as vz

# Note: gauge takes a single value. Use grid() with multiple single-value gauges
# to build a gauge cluster, or compose with page/tab.
chart = vz.page(charts=[
vz.gauge(value=72, title='CPU'),
vz.gauge(value=88, title='Memory'),
vz.gauge(value=45, title='Disk I/O'),
vz.liquid(value=0.65, title='Storage'),
], title="Infrastructure Status")
chart.to_html()

What makes ops themes different

ThemeVibeBest for
ops_grafanaDense grids, muted animationPrometheus/Grafana-style dashboards
ops_cloudwatchBlue-toned, service-orientedAWS monitoring views
ops_kibanaDark, log-centricElasticsearch log analysis

These are visual inspiration only, not affiliated with Grafana Labs, AWS, or Elastic.