- pill: two host dots -> ONE consolidated state (down > slow > up) — the at-a-glance question is 'can I watch?', which is one state; per-host detail belongs in the tap panel - panel: dashed slow-threshold line in the CDN sparkline (drawn at the server's real threshold, not a client copy) + origin up/down step sparkline so 'how long has the origin been down' is visible - server: origin probe keeps a 20-sample hist like the CDN probe; DEGRADED threshold is now ANIWEB_CDN_KBPS (default 40) and is returned in /api/cdn so the UI draws the line at the live value - tests: pill assertions switched to consolidated states; fixtures carry origin hist + threshold; assert both sparklines + threshold line - docs: README + SPEC synced; preview on :8322 restarted (pid 44382)
41 lines
1.7 KiB
HTML
41 lines
1.7 KiB
HTML
<!doctype html>
|
|
<html>
|
|
<head>
|
|
<meta charset="utf-8">
|
|
<meta name="viewport" content="width=device-width, initial-scale=1">
|
|
<meta name="theme-color" content="#0e0f13">
|
|
<meta name="mobile-web-app-capable" content="yes">
|
|
<meta name="apple-mobile-web-app-capable" content="yes">
|
|
<title>ani-web</title>
|
|
<link rel="icon" href="icon.svg">
|
|
<link rel="manifest" href="manifest.webmanifest">
|
|
|
|
<link rel="stylesheet" href="style.css?v={{VERSION}}">
|
|
</head>
|
|
<body>
|
|
<header>
|
|
<a class="logo" href="/">ani-web</a>
|
|
<form onsubmit="const q=document.getElementById('q').value.trim(); if(q) location='?q='+encodeURIComponent(q); return false">
|
|
<input id="q" placeholder="search anime…" aria-label="search anime" autocomplete="off" autocapitalize="off" spellcheck="false">
|
|
</form>
|
|
<span id="pill" class="pill"><i class="d"></i><span></span></span>
|
|
<span id="me" class="muted"></span>
|
|
<div id="menubox" style="display:none">
|
|
<button id="menu" class="tiny" aria-label="menu" aria-haspopup="true">☰</button>
|
|
<div id="menu-items">
|
|
<a id="stats" class="tiny" href="?stats">stats</a>
|
|
<button id="logout" class="tiny">logout</button>
|
|
<button id="delacct" class="tiny danger">delete account</button>
|
|
</div>
|
|
</div>
|
|
</header>
|
|
<main id="main"><p class="muted">Search for an anime to get started.</p></main>
|
|
<div id="toasts" aria-live="polite"></div>
|
|
<!-- Versioning: ?v={{VERSION}} is replaced by the server (server/app.py index
|
|
route) with the git SHA at startup — a correct cache key per commit.
|
|
No hand-bumping; JSV in app.js reads the same value from its own URL. -->
|
|
<script src="hls.min.js"></script>
|
|
<script src="app.js?v={{VERSION}}"></script>
|
|
</body>
|
|
</html>
|