{{define "logs.html"}} {{template "base" .}} {{end}} {{define "content"}} {{template "logs-card" .}} {{end}} {{/* The whole card is the htmx swap target for tab changes — server re-renders the strip with the right tab marked active each time, no JS state to sync. Side effect: filter clears on tab change, which matches "new log, fresh look" intent. Load earlier walks back through the current file; once exhausted, the button re-labels to "Load previous from " and starts paging into rotated archives. Live tail is JS-driven via EventSource and survives only within a tab; switching tabs closes the stream. */}} {{define "logs-card"}}
Logs
{{range .Sources}} {{end}}
{{template "logs-body" .}}
{{end}} {{define "logs-body"}}
Download
{{if .Source.Lines}}
{{/* sourceContent's field names mirror earlierData so the same logs-earlier template renders both the initial buffer (.Source) and the Earlier-handler response. */}} {{template "logs-earlier" .Source}}
Source: {{.Source.Path}}
{{else}}

No entries in {{.Source.Path}} yet.

{{end}}
{{end}} {{/* Combined load-more button + lines fragment. Used both as the initial buffer and as the response to /earlier requests — the old button is replaced via outerHTML by [new button, new lines], keeping chronology in the DOM correct. The button's label depends on whether the next click stays in the current file ("Load earlier") or crosses into a rotation ("Load previous from messages.0"). */}} {{define "logs-earlier"}} {{with .Next}} {{end}}{{range .Lines}}
{{.Text}}
{{end}}{{end}}