228 lines
9.0 KiB
HTML
228 lines
9.0 KiB
HTML
|
|
<!DOCTYPE html>
|
||
|
|
<html lang="en">
|
||
|
|
<head>
|
||
|
|
<meta charset="UTF-8">
|
||
|
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||
|
|
<title>Status Page Example</title>
|
||
|
|
<script type="module" src="./dist_bundle/bundle.js"></script>
|
||
|
|
<style>
|
||
|
|
body {
|
||
|
|
margin: 0;
|
||
|
|
padding: 0;
|
||
|
|
font-family: 'Geist Sans', -apple-system, BlinkMacSystemFont, sans-serif;
|
||
|
|
background: #fafafa;
|
||
|
|
}
|
||
|
|
@media (prefers-color-scheme: dark) {
|
||
|
|
body {
|
||
|
|
background: #09090b;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
.page-container {
|
||
|
|
min-height: 100vh;
|
||
|
|
display: flex;
|
||
|
|
flex-direction: column;
|
||
|
|
}
|
||
|
|
main {
|
||
|
|
flex: 1;
|
||
|
|
}
|
||
|
|
</style>
|
||
|
|
</head>
|
||
|
|
<body>
|
||
|
|
<div class="page-container">
|
||
|
|
<!-- Header -->
|
||
|
|
<upl-statuspage-header
|
||
|
|
title="System Status"
|
||
|
|
brandName="Example Corp"
|
||
|
|
description="Real-time status of our services"
|
||
|
|
></upl-statuspage-header>
|
||
|
|
|
||
|
|
<!-- Status Bar -->
|
||
|
|
<upl-statuspage-statusbar></upl-statuspage-statusbar>
|
||
|
|
|
||
|
|
<!-- Stats Grid - NEW COMPONENT -->
|
||
|
|
<upl-statuspage-statsgrid
|
||
|
|
uptime="99.95"
|
||
|
|
avgResponseTime="125"
|
||
|
|
totalIncidents="0"
|
||
|
|
affectedServices="0"
|
||
|
|
totalServices="12"
|
||
|
|
currentStatus="operational"
|
||
|
|
timePeriod="90 days"
|
||
|
|
></upl-statuspage-statsgrid>
|
||
|
|
|
||
|
|
<main>
|
||
|
|
<!-- Assets Selector -->
|
||
|
|
<upl-statuspage-assetsselector></upl-statuspage-assetsselector>
|
||
|
|
|
||
|
|
<!-- Status Details (48 hours) -->
|
||
|
|
<upl-statuspage-statusdetails
|
||
|
|
serviceName="API Gateway"
|
||
|
|
hoursToShow="48"
|
||
|
|
></upl-statuspage-statusdetails>
|
||
|
|
|
||
|
|
<!-- Status Month -->
|
||
|
|
<upl-statuspage-statusmonth
|
||
|
|
serviceName="API Gateway"
|
||
|
|
monthsToShow="3"
|
||
|
|
></upl-statuspage-statusmonth>
|
||
|
|
|
||
|
|
<!-- Incidents -->
|
||
|
|
<upl-statuspage-incidents
|
||
|
|
daysToShow="90"
|
||
|
|
></upl-statuspage-incidents>
|
||
|
|
</main>
|
||
|
|
|
||
|
|
<!-- Footer -->
|
||
|
|
<upl-statuspage-footer
|
||
|
|
showPoweredBy="true"
|
||
|
|
showApiLink="true"
|
||
|
|
></upl-statuspage-footer>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<script>
|
||
|
|
// Example: Initialize with demo data
|
||
|
|
document.addEventListener('DOMContentLoaded', () => {
|
||
|
|
// Status bar data
|
||
|
|
const statusBar = document.querySelector('upl-statuspage-statusbar');
|
||
|
|
if (statusBar) {
|
||
|
|
statusBar.overallStatus = {
|
||
|
|
status: 'operational',
|
||
|
|
message: 'All systems operational',
|
||
|
|
lastUpdated: Date.now(),
|
||
|
|
affectedServices: 0,
|
||
|
|
totalServices: 12
|
||
|
|
};
|
||
|
|
}
|
||
|
|
|
||
|
|
// Assets selector data
|
||
|
|
const assetsSelector = document.querySelector('upl-statuspage-assetsselector');
|
||
|
|
if (assetsSelector) {
|
||
|
|
assetsSelector.services = [
|
||
|
|
{
|
||
|
|
id: 'api-gateway',
|
||
|
|
displayName: 'API Gateway',
|
||
|
|
category: 'Core Services',
|
||
|
|
description: 'Main API endpoint',
|
||
|
|
currentStatus: 'operational',
|
||
|
|
selected: true
|
||
|
|
},
|
||
|
|
{
|
||
|
|
id: 'web-app',
|
||
|
|
displayName: 'Web Application',
|
||
|
|
category: 'Frontend',
|
||
|
|
description: 'Customer-facing web app',
|
||
|
|
currentStatus: 'operational',
|
||
|
|
selected: true
|
||
|
|
},
|
||
|
|
{
|
||
|
|
id: 'database',
|
||
|
|
displayName: 'Database Cluster',
|
||
|
|
category: 'Core Services',
|
||
|
|
description: 'Primary data storage',
|
||
|
|
currentStatus: 'operational',
|
||
|
|
selected: true
|
||
|
|
},
|
||
|
|
{
|
||
|
|
id: 'cdn',
|
||
|
|
displayName: 'CDN',
|
||
|
|
category: 'Infrastructure',
|
||
|
|
description: 'Content delivery network',
|
||
|
|
currentStatus: 'operational',
|
||
|
|
selected: false
|
||
|
|
}
|
||
|
|
];
|
||
|
|
}
|
||
|
|
|
||
|
|
// Status details data (48 hours)
|
||
|
|
const statusDetails = document.querySelector('upl-statuspage-statusdetails');
|
||
|
|
if (statusDetails) {
|
||
|
|
const now = Date.now();
|
||
|
|
statusDetails.historyData = Array.from({ length: 48 }, (_, i) => {
|
||
|
|
const date = new Date();
|
||
|
|
date.setMinutes(0, 0, 0);
|
||
|
|
date.setHours(date.getHours() - (47 - i));
|
||
|
|
return {
|
||
|
|
timestamp: date.getTime(),
|
||
|
|
status: Math.random() > 0.95 ? 'degraded' : 'operational',
|
||
|
|
responseTime: 50 + Math.random() * 50,
|
||
|
|
errorRate: 0
|
||
|
|
};
|
||
|
|
});
|
||
|
|
}
|
||
|
|
|
||
|
|
// Monthly data
|
||
|
|
const statusMonth = document.querySelector('upl-statuspage-statusmonth');
|
||
|
|
if (statusMonth) {
|
||
|
|
const generateMonthData = (monthOffset) => {
|
||
|
|
const date = new Date();
|
||
|
|
date.setMonth(date.getMonth() - monthOffset);
|
||
|
|
const year = date.getFullYear();
|
||
|
|
const month = date.getMonth();
|
||
|
|
const daysInMonth = new Date(year, month + 1, 0).getDate();
|
||
|
|
|
||
|
|
return {
|
||
|
|
month: `${year}-${(month + 1).toString().padStart(2, '0')}`,
|
||
|
|
days: Array.from({ length: daysInMonth }, (_, i) => ({
|
||
|
|
date: `${year}-${(month + 1).toString().padStart(2, '0')}-${(i + 1).toString().padStart(2, '0')}`,
|
||
|
|
uptime: Math.random() > 0.05 ? 100 : 95 + Math.random() * 5,
|
||
|
|
status: Math.random() > 0.05 ? 'operational' : 'degraded',
|
||
|
|
incidents: Math.random() > 0.05 ? 0 : 1,
|
||
|
|
totalDowntime: 0
|
||
|
|
})),
|
||
|
|
overallUptime: 99.5 + Math.random() * 0.5,
|
||
|
|
totalIncidents: Math.floor(Math.random() * 3)
|
||
|
|
};
|
||
|
|
};
|
||
|
|
|
||
|
|
statusMonth.monthlyData = [
|
||
|
|
generateMonthData(0),
|
||
|
|
generateMonthData(1),
|
||
|
|
generateMonthData(2)
|
||
|
|
];
|
||
|
|
}
|
||
|
|
|
||
|
|
// Incidents data
|
||
|
|
const incidents = document.querySelector('upl-statuspage-incidents');
|
||
|
|
if (incidents) {
|
||
|
|
incidents.currentIncidents = [];
|
||
|
|
incidents.pastIncidents = [
|
||
|
|
{
|
||
|
|
id: 'inc-001',
|
||
|
|
title: 'Database connection pool exhaustion',
|
||
|
|
severity: 'minor',
|
||
|
|
startTime: Date.now() - 7 * 24 * 60 * 60 * 1000,
|
||
|
|
endTime: Date.now() - 7 * 24 * 60 * 60 * 1000 + 2 * 60 * 60 * 1000,
|
||
|
|
impact: 'Slower response times for some API endpoints',
|
||
|
|
affectedServices: ['API Gateway', 'Database Cluster'],
|
||
|
|
updates: [
|
||
|
|
{
|
||
|
|
id: 'update-1',
|
||
|
|
timestamp: Date.now() - 7 * 24 * 60 * 60 * 1000,
|
||
|
|
status: 'investigating',
|
||
|
|
message: 'We are investigating reports of slow API responses',
|
||
|
|
author: 'Engineering Team'
|
||
|
|
},
|
||
|
|
{
|
||
|
|
id: 'update-2',
|
||
|
|
timestamp: Date.now() - 7 * 24 * 60 * 60 * 1000 + 30 * 60 * 1000,
|
||
|
|
status: 'identified',
|
||
|
|
message: 'The issue has been identified as database connection pool exhaustion',
|
||
|
|
author: 'Engineering Team'
|
||
|
|
},
|
||
|
|
{
|
||
|
|
id: 'update-3',
|
||
|
|
timestamp: Date.now() - 7 * 24 * 60 * 60 * 1000 + 2 * 60 * 60 * 1000,
|
||
|
|
status: 'resolved',
|
||
|
|
message: 'Connection pool settings have been adjusted and performance is back to normal',
|
||
|
|
author: 'Engineering Team'
|
||
|
|
}
|
||
|
|
],
|
||
|
|
rootCause: 'Insufficient connection pool size for peak traffic',
|
||
|
|
resolution: 'Increased connection pool size and implemented better connection management'
|
||
|
|
}
|
||
|
|
];
|
||
|
|
}
|
||
|
|
});
|
||
|
|
</script>
|
||
|
|
</body>
|
||
|
|
</html>
|