zenith-backend / monitoring /ultra_simple_dashboard.py
teoat's picture
Upload folder using huggingface_hub
4ae946d verified
#!/usr/bin/env python3
"""
Ultra Simple Production Monitoring Dashboard
Minimal dependencies - uses only standard library
"""
import json
import time
from datetime import datetime
from http.server import BaseHTTPRequestHandler, HTTPServer
try:
import requests # type: ignore
except ImportError:
requests = None # type: ignore
# Simple metrics store
metrics = {"cpu_percent": [], "memory_percent": [], "disk_percent": [], "timestamps": [], "system_info": {}}
class MonitoringDashboardHandler(BaseHTTPRequestHandler):
def do_GET(self):
if self.path == "/":
self.serve_dashboard()
elif self.path == "/api/metrics":
self.serve_metrics()
elif self.path == "/api/health":
self.serve_health()
elif self.path == "/api/environments":
self.serve_environments()
else:
self.send_404()
def serve_dashboard(self):
self.send_response(200)
self.send_header("Content-type", "text/html")
self.end_headers()
html = """
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Production Monitoring Dashboard</title>
<style>
* { margin: 0; padding: 0; box-sizing: border-box; }
body {
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
background: linear-gradient(135deg, #1e3c72 0%, #2a5298 100%);
color: white; min-height: 100vh;
}
.container { max-width: 1200px; margin: 0 auto; padding: 20px; }
.header { text-align: center; margin-bottom: 40px; }
.header h1 { font-size: 2.5rem; margin-bottom: 10px; }
.header p { font-size: 1.1rem; opacity: 0.8; }
.metrics-grid {
display: grid; grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
gap: 20px; margin-bottom: 40px;
}
.metric-card {
background: rgba(255, 255, 255, 0.1); backdrop-filter: blur(10px);
border-radius: 15px; padding: 25px; border: 1px solid rgba(255, 255, 255, 0.2);
transition: transform 0.3s ease;
}
.metric-card:hover { transform: translateY(-5px); }
.metric-title { font-size: 1.2rem; margin-bottom: 15px; color: #64b5f6; }
.metric-value { font-size: 2rem; font-weight: bold; margin-bottom: 5px; }
.metric-label { font-size: 0.9rem; opacity: 0.7; }
.env-card {
background: rgba(255, 255, 255, 0.15); backdrop-filter: blur(10px);
border-radius: 15px; padding: 20px; margin-bottom: 20px;
border: 2px solid rgba(255, 255, 255, 0.3);
}
.env-blue { border-color: #4fc3f7; }
.env-green { border-color: #66bb6a; }
.env-status { display: flex; align-items: center; margin-bottom: 10px; }
.env-indicator { width: 16px; height: 16px; border-radius: 50%; margin-right: 10px; }
.status-healthy { background: #4caf50; }
.status-unhealthy { background: #f44336; }
.status-unknown { background: #ff9800; }
.refresh-btn {
background: #64b5f6; color: white; border: none; padding: 10px 20px;
border-radius: 25px; cursor: pointer; font-size: 1rem;
transition: background 0.3s ease;
}
.refresh-btn:hover { background: #42a5f5; }
.last-updated { text-align: center; opacity: 0.7; margin-top: 20px; }
.two-column { display: grid; grid-template-columns: 1fr 1fr; gap: 20px; }
</style>
</head>
<body>
<div class="container">
<div class="header">
<h1>πŸš€ Production Monitoring Dashboard</h1>
<p>Real-time system and application monitoring</p>
<button class="refresh-btn" onclick="refreshData()">πŸ”„ Refresh Data</button>
</div>
<div class="section-title">πŸ’» System Resources</div>
<div class="metrics-grid">
<div class="metric-card">
<div class="metric-title">πŸ–₯️ CPU Usage</div>
<div class="metric-value" id="cpu-value">--%</div>
<div class="metric-label">Processing load</div>
</div>
<div class="metric-card">
<div class="metric-title">🧠 Memory Usage</div>
<div class="metric-value" id="memory-value">--%</div>
<div class="metric-label">Memory consumption</div>
</div>
<div class="metric-card">
<div class="metric-title">πŸ’Ύ Disk Usage</div>
<div class="metric-value" id="disk-value">--%</div>
<div class="metric-label">Storage utilization</div>
</div>
<div class="metric-card">
<div class="metric-title">⏱️ Uptime</div>
<div class="metric-value" id="uptime-value">--</div>
<div class="metric-label">System running time</div>
</div>
</div>
<div class="section-title">🌍 Deployment Environments</div>
<div class="two-column">
<div class="env-card env-blue">
<div style="font-size: 1.3rem; margin-bottom: 15px;">πŸ”΅ Blue Environment</div>
<div class="env-status">
<div id="blue-status-indicator" class="env-indicator status-unknown"></div>
<span id="blue-status-text">Checking...</span>
</div>
<div style="font-size: 1.1rem;" id="blue-response-time">Response Time: --ms</div>
<div style="font-size: 1.1rem;" id="blue-endpoint">Endpoint: http://localhost:5002</div>
</div>
<div class="env-card env-green">
<div style="font-size: 1.3rem; margin-bottom: 15px;">🟒 Green Environment</div>
<div class="env-status">
<div id="green-status-indicator" class="env-indicator status-unknown"></div>
<span id="green-status-text">Checking...</span>
</div>
<div style="font-size: 1.1rem;" id="green-response-time">Response Time: --ms</div>
<div style="font-size: 1.1rem;" id="green-endpoint">Endpoint: http://localhost:5003</div>
</div>
</div>
<div class="last-updated" id="last-updated">
Last updated: Loading...
</div>
</div>
<script>
async function fetchEndpoint(endpoint) {
try {
const response = await fetch(endpoint);
return await response.json();
} catch (error) {
console.error('Error fetching', endpoint, ':', error);
return null;
}
}
function updateDashboard(data) {
if (!data) return;
document.getElementById('cpu-value').textContent = data.cpu_percent?.toFixed(1) + '%' || '--%';
document.getElementById('memory-value').textContent = data.memory_percent?.toFixed(1) + '%' || '--%';
document.getElementById('disk-value').textContent = data.disk_percent?.toFixed(1) + '%' || '--%';
document.getElementById('uptime-value').textContent = data.uptime || '--';
document.getElementById('last-updated').textContent =
'Last updated: ' + new Date().toLocaleTimeString();
}
function updateEnvironments(data) {
if (!data) return;
const blueHealthy = data.blue_environment?.healthy || false;
const blueTime = data.blue_environment?.response_time || 0;
document.getElementById('blue-status-indicator').className =
'env-indicator ' + (blueHealthy ? 'status-healthy' : 'status-unhealthy');
document.getElementById('blue-status-text').textContent =
blueHealthy ? 'Healthy' : 'Unhealthy';
document.getElementById('blue-response-time').textContent =
'Response Time: ' + blueTime + 'ms';
const greenHealthy = data.green_environment?.healthy || false;
const greenTime = data.green_environment?.response_time || 0;
document.getElementById('green-status-indicator').className =
'env-indicator ' + (greenHealthy ? 'status-healthy' : 'status-unhealthy');
document.getElementById('green-status-text').textContent =
greenHealthy ? 'Healthy' : 'Unhealthy';
document.getElementById('green-response-time').textContent =
'Response Time: ' + greenTime + 'ms';
}
async function refreshData() {
const [metrics, environments] = await Promise.all([
fetchEndpoint('/api/metrics'),
fetchEndpoint('/api/environments')
]);
updateDashboard(metrics);
updateEnvironments(environments);
}
setInterval(refreshData, 5000);
refreshData();
</script>
</body>
</html>
"""
self.wfile.write(html.encode())
def serve_metrics(self):
self.send_response(200)
self.send_header("Content-type", "application/json")
self.end_headers()
current_metrics = collect_system_metrics()
response = json.dumps(current_metrics, indent=2)
self.wfile.write(response.encode())
def serve_health(self):
self.send_response(200)
self.send_header("Content-type", "application/json")
self.end_headers()
health_data = {
"status": "healthy",
"timestamp": datetime.now().isoformat(),
"version": "1.0.0",
"uptime": time.time() - start_time,
}
response = json.dumps(health_data, indent=2)
self.wfile.write(response.encode())
def serve_environments(self):
self.send_response(200)
self.send_header("Content-type", "application/json")
self.end_headers()
env_data = collect_environment_metrics()
response = json.dumps(env_data, indent=2)
self.wfile.write(response.encode())
def send_404(self):
self.send_response(404)
self.send_header("Content-type", "text/html")
self.end_headers()
self.wfile.write(b"404 Not Found")
def log_message(self, format, *args):
pass
def collect_system_metrics():
"""Collect system metrics using standard library"""
try:
import psutil
cpu_percent = psutil.cpu_percent(interval=1)
memory = psutil.virtual_memory()
disk = psutil.disk_usage("/")
return {
"cpu_percent": cpu_percent,
"memory_percent": memory.percent,
"memory_available_gb": memory.available / (1024**3),
"disk_percent": disk.percent,
"disk_free_gb": disk.free / (1024**3),
"uptime": time.strftime("%H:%M:%S", time.gmtime(time.time() - start_time)),
"timestamp": datetime.now().isoformat(),
"process_count": len(psutil.pids()),
}
except ImportError:
import random
cpu = random.uniform(20, 80)
memory = random.uniform(30, 70)
disk = random.uniform(40, 60)
return {
"cpu_percent": cpu,
"memory_percent": memory,
"memory_available_gb": random.uniform(2, 8),
"disk_percent": disk,
"disk_free_gb": random.uniform(10, 50),
"uptime": time.strftime("%H:%M:%S", time.gmtime(time.time() - start_time)),
"timestamp": datetime.now().isoformat(),
"process_count": random.randint(100, 300),
}
def collect_environment_metrics():
"""Collect blue-green environment health metrics"""
environments = {}
# Check Blue Environment (port 5002)
blue_health = check_environment_health("localhost", 5002)
environments["blue_environment"] = blue_health
# Check Green Environment (port 5003)
green_health = check_environment_health("localhost", 5003)
environments["green_environment"] = green_health
environments["timestamp"] = datetime.now().isoformat()
return environments
def check_environment_health(host, port):
"""Check if environment is healthy"""
try:
start_time = time.time()
response = requests.get(f"http://{host}:{port}/api/health", timeout=5)
response_time = (time.time() - start_time) * 1000
if response.status_code == 200:
try:
health_data = response.json()
return {
"healthy": True,
"response_time": int(response_time),
"status": "healthy",
"version": health_data.get("version", "unknown"),
"endpoint": f"http://{host}:{port}",
"last_check": datetime.now().isoformat(),
}
except Exception:
return {
"healthy": True,
"response_time": int(response_time),
"status": "healthy",
"endpoint": f"http://{host}:{port}",
"last_check": datetime.now().isoformat(),
}
else:
return {
"healthy": False,
"response_time": int(response_time),
"status": "unhealthy",
"error": f"HTTP {response.status_code}",
"endpoint": f"http://{host}:{port}",
"last_check": datetime.now().isoformat(),
}
except requests.exceptions.RequestException as e:
return {
"healthy": False,
"response_time": 5000,
"status": "unreachable",
"error": str(e),
"endpoint": f"http://{host}:{port}",
"last_check": datetime.now().isoformat(),
}
except Exception as e:
return {
"healthy": False,
"response_time": 0,
"status": "error",
"error": str(e),
"endpoint": f"http://{host}:{port}",
"last_check": datetime.now().isoformat(),
}
def run_server():
"""Run the monitoring server"""
server_address = ("", 8080)
httpd = HTTPServer(server_address, MonitoringDashboardHandler)
print("πŸš€ Production Monitoring Dashboard started!")
print("πŸ“Š Access URL: http://localhost:8080")
print("🌍 Blue-Green Environment Monitoring: Enabled")
print("πŸ”„ Auto-refresh: Every 5 seconds")
print("⏹️ To stop: Press Ctrl+C")
print("")
try:
httpd.serve_forever()
except KeyboardInterrupt:
print("\\nπŸ›‘ Dashboard stopped by user")
httpd.server_close()
if __name__ == "__main__":
start_time = time.time()
run_server()