fillRegistrySummary derived LastResult from whichever single checks row happened to have the latest checked_at, not the cycle's actual aggregated result — a cycle with a mix of passing and failing checks (e.g. one egress target timed out while the rest, including the chronologically-last check, succeeded) rendered as a green "pass" badge on /registry, disagreeing with the correct "partial" badge already shown on /ips for the same address. Now prefers ip_queue.overall_result (the orchestrator's own aggregation) when a live queue row has a finished cycle, leaves the badge blank while a cycle is still in progress, and only falls back to classifying the most recent cycle's own checks (pass/fail/partial) once the address has been deleted from the queue and overall_result is no longer available. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
61 lines
2.9 KiB
HTML
61 lines
2.9 KiB
HTML
{{define "registry_detail_page"}}
|
||
<!doctype html>
|
||
<html lang="ru">
|
||
<head>{{template "html_head" .}}</head>
|
||
<body>
|
||
<div class="bg-grid"></div>
|
||
<input type="checkbox" id="nav-toggle" class="nav-toggle">
|
||
<div class="shell">
|
||
{{template "sidebar_nav" .}}
|
||
<div>
|
||
{{template "topbar_mobile" .}}
|
||
<main class="main">
|
||
<div id="error-banner">{{template "banner_inner" .Banner}}</div>
|
||
{{template "registry_detail_content" .}}
|
||
</main>
|
||
</div>
|
||
</div>
|
||
</body>
|
||
</html>
|
||
{{end}}
|
||
|
||
{{define "registry_detail_content"}}
|
||
<p><a href="/registry">← К реестру</a></p>
|
||
<div class="topbar">
|
||
<h1 class="mono" style="display:flex;align-items:center;gap:10px">{{.History.Registry.IPAddress}}
|
||
{{if eq .History.Registry.LastResult "pass"}}<span class="pill pill-success">pass</span>
|
||
{{else if eq .History.Registry.LastResult "partial"}}<span class="pill pill-warning">partial</span>
|
||
{{else if eq .History.Registry.LastResult "fail"}}<span class="pill pill-danger">fail</span>
|
||
{{else if eq .History.Registry.LastResult "cancelled"}}<span class="pill pill-cancel">cancelled</span>{{end}}
|
||
{{if .History.Registry.InQueue}}<a class="pill pill-info" href="/ips/{{.History.Registry.IPAddress}}">{{.History.Registry.CurrentState}} · в очереди</a>{{else}}<span class="pill pill-neutral">не в очереди</span>{{end}}
|
||
</h1>
|
||
</div>
|
||
<p class="muted">
|
||
впервые замечен: {{fmtTime .History.Registry.FirstSeenAt}} · последний раз замечен: {{fmtTime .History.Registry.LastSeenAt}}
|
||
· всего циклов проверки: {{.History.Registry.TotalCycles}}
|
||
</p>
|
||
|
||
<h2 class="section-title">История проверок (все сохранённые циклы)</h2>
|
||
{{if .History.Checks}}
|
||
<div class="panel">
|
||
<div class="table-scroll">
|
||
<table>
|
||
<thead><tr><th>Цикл</th><th>Источник</th><th>Тип</th><th>Цель</th><th>Успех</th><th>Задержка, мс</th><th>Время</th><th>Детали</th></tr></thead>
|
||
<tbody>
|
||
{{range .History.Checks}}
|
||
<tr>
|
||
<td class="num" data-label="Цикл">{{.CycleID}}</td>
|
||
<td data-label="Источник">{{.Source}}</td><td data-label="Тип">{{.CheckType}}</td><td class="addr" data-label="Цель">{{.Target}}</td>
|
||
<td data-label="Успех">{{if .Success}}<span class="pill pill-success">ok</span>{{else}}<span class="pill pill-danger">fail</span>{{end}}</td>
|
||
<td class="num" data-label="Задержка, мс">{{.LatencyMS}}</td><td class="num" data-label="Время">{{fmtTime .CheckedAt}}</td><td data-label="Детали">{{.Detail}}</td>
|
||
</tr>
|
||
{{end}}
|
||
</tbody>
|
||
</table>
|
||
</div>
|
||
</div>
|
||
<p class="muted" style="margin-top:8px">Если глубина истории (см. <a href="/settings">настройки</a>) ограничена, здесь
|
||
показаны только сохранённые циклы — более старые уже вытеснены.</p>
|
||
{{else}}<p class="muted">Проверок пока нет.</p>{{end}}
|
||
{{end}}
|