mirror of
https://github.com/asimonson1125/asimonson1125.github.io.git
synced 2026-02-25 05:09:49 -06:00
Compare commits
3 Commits
b59842899b
...
085ade75bf
| Author | SHA1 | Date | |
|---|---|---|---|
| 085ade75bf | |||
| dae0882e0f | |||
| d0f50141c7 |
@@ -33,8 +33,12 @@ SERVICES = [
|
|||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
|
||||||
# Check interval: 30 mins
|
# Check interval: 1 min
|
||||||
CHECK_INTERVAL = 1800
|
CHECK_INTERVAL = 60
|
||||||
|
|
||||||
|
# Retention: 90 days (quarter year)
|
||||||
|
RETENTION_DAYS = 90
|
||||||
|
CLEANUP_INTERVAL = 86400 # 24 hours
|
||||||
|
|
||||||
DATABASE_URL = os.environ.get('DATABASE_URL')
|
DATABASE_URL = os.environ.get('DATABASE_URL')
|
||||||
|
|
||||||
@@ -273,14 +277,13 @@ class ServiceMonitor:
|
|||||||
if total_count == 0:
|
if total_count == 0:
|
||||||
return None
|
return None
|
||||||
|
|
||||||
# Minimum-data thresholds
|
# Only show uptime for a window if we have data older than it
|
||||||
if hours:
|
if hours:
|
||||||
expected_checks = (hours * 3600) / CHECK_INTERVAL
|
cur.execute(
|
||||||
minimum_checks = max(3, expected_checks * 0.5)
|
'SELECT EXISTS(SELECT 1 FROM service_checks WHERE service_id = %s AND timestamp <= %s)',
|
||||||
if total_count < minimum_checks:
|
(service_id, cutoff),
|
||||||
return None
|
)
|
||||||
else:
|
if not cur.fetchone()[0]:
|
||||||
if total_count < 3:
|
|
||||||
return None
|
return None
|
||||||
|
|
||||||
return round((online_count / total_count) * 100, 2)
|
return round((online_count / total_count) * 100, 2)
|
||||||
@@ -341,20 +344,44 @@ class ServiceMonitor:
|
|||||||
finally:
|
finally:
|
||||||
conn.close()
|
conn.close()
|
||||||
|
|
||||||
|
def _purge_old_records(self):
|
||||||
|
"""Delete check records older than RETENTION_DAYS."""
|
||||||
|
conn = self._get_conn()
|
||||||
|
if conn is None:
|
||||||
|
return
|
||||||
|
try:
|
||||||
|
cutoff = datetime.now() - timedelta(days=RETENTION_DAYS)
|
||||||
|
with conn, conn.cursor() as cur:
|
||||||
|
cur.execute(
|
||||||
|
'DELETE FROM service_checks WHERE timestamp < %s',
|
||||||
|
(cutoff,),
|
||||||
|
)
|
||||||
|
deleted = cur.rowcount
|
||||||
|
if deleted:
|
||||||
|
print(f"Purged {deleted} records older than {RETENTION_DAYS} days")
|
||||||
|
finally:
|
||||||
|
conn.close()
|
||||||
|
|
||||||
def start_monitoring(self):
|
def start_monitoring(self):
|
||||||
"""Start background monitoring thread"""
|
"""Start background monitoring thread"""
|
||||||
def monitor_loop():
|
def monitor_loop():
|
||||||
# Initial check
|
|
||||||
self.check_all_services()
|
self.check_all_services()
|
||||||
|
self._purge_old_records()
|
||||||
|
|
||||||
|
checks_since_cleanup = 0
|
||||||
|
checks_per_cleanup = CLEANUP_INTERVAL // CHECK_INTERVAL
|
||||||
|
|
||||||
# Periodic checks
|
|
||||||
while True:
|
while True:
|
||||||
time.sleep(CHECK_INTERVAL)
|
time.sleep(CHECK_INTERVAL)
|
||||||
self.check_all_services()
|
self.check_all_services()
|
||||||
|
checks_since_cleanup += 1
|
||||||
|
if checks_since_cleanup >= checks_per_cleanup:
|
||||||
|
self._purge_old_records()
|
||||||
|
checks_since_cleanup = 0
|
||||||
|
|
||||||
thread = Thread(target=monitor_loop, daemon=True)
|
thread = Thread(target=monitor_loop, daemon=True)
|
||||||
thread.start()
|
thread.start()
|
||||||
print(f"Service monitoring started (checks every {CHECK_INTERVAL/3600} hours)")
|
print(f"Service monitoring started (checks every {CHECK_INTERVAL} seconds)")
|
||||||
|
|
||||||
# Global monitor instance
|
# Global monitor instance
|
||||||
monitor = ServiceMonitor()
|
monitor = ServiceMonitor()
|
||||||
|
|||||||
@@ -244,8 +244,8 @@ function initStatusPage() {
|
|||||||
clearInterval(statusIntervalId);
|
clearInterval(statusIntervalId);
|
||||||
}
|
}
|
||||||
fetchStatus();
|
fetchStatus();
|
||||||
// Auto-refresh every 5 minutes to get latest data
|
// Auto-refresh every 1 minute to get latest data
|
||||||
statusIntervalId = setInterval(fetchStatus, 300000);
|
statusIntervalId = setInterval(fetchStatus, 60000);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Clean up interval when navigating away via SPA
|
// Clean up interval when navigating away via SPA
|
||||||
|
|||||||
@@ -53,7 +53,7 @@
|
|||||||
<link rel="canonical" href="{{ request.url_root | trim('/') }}{{ var['canonical'] }}" />
|
<link rel="canonical" href="{{ request.url_root | trim('/') }}{{ var['canonical'] }}" />
|
||||||
<script defer src="{{ url_for('static', filename='js/checkbox.js') }}"></script>
|
<script defer src="{{ url_for('static', filename='js/checkbox.js') }}"></script>
|
||||||
<script defer src="{{ url_for('static', filename='js/responsive.js') }}"></script>
|
<script defer src="{{ url_for('static', filename='js/responsive.js') }}"></script>
|
||||||
<script src="{{ url_for('static', filename='js/chessbed.js') }}"></script>
|
{# <script src="{{ url_for('static', filename='js/chessbed.js') }}"></script> #}
|
||||||
<script defer src="{{ url_for('static', filename='js/idler.js') }}"></script>
|
<script defer src="{{ url_for('static', filename='js/idler.js') }}"></script>
|
||||||
<script defer src="https://cdn.jsdelivr.net/npm/p5@1.4.1/lib/p5.min.js"></script>
|
<script defer src="https://cdn.jsdelivr.net/npm/p5@1.4.1/lib/p5.min.js"></script>
|
||||||
<title>{{ var['title'] }}</title>
|
<title>{{ var['title'] }}</title>
|
||||||
|
|||||||
@@ -91,8 +91,8 @@
|
|||||||
<div class="info-box">
|
<div class="info-box">
|
||||||
<h4>About This Monitor</h4>
|
<h4>About This Monitor</h4>
|
||||||
<ul>
|
<ul>
|
||||||
<li><strong>Check Frequency:</strong> Services are checked automatically every 30 minutes from the server</li>
|
<li><strong>Check Frequency:</strong> Services are checked automatically every minute from the server</li>
|
||||||
<li><strong>Page Refresh:</strong> This page auto-refreshes every 5 minutes to show latest data</li>
|
<li><strong>Page Refresh:</strong> This page auto-refreshes every minute to show latest data</li>
|
||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
Reference in New Issue
Block a user