2026-05-31 21:52:56 +03:00
{{define "admin_logs.html"}}{{template "base" .}}{{end}}
{{define "content"}}
< section class = "app-shell admin-shell" aria-labelledby = "admin-logs-title" >
< aside class = "app-sidebar" >
< nav class = "sidebar-nav" >
< a class = "sidebar-link" href = "/admin" > {{template "icon-dashboard" .}}< span > Overview< / span > < / a >
< a class = "sidebar-link" href = "/admin/files" > {{template "icon-folder" .}}< span > Files< / span > < / a >
< a class = "sidebar-link" href = "/admin/users" > {{template "icon-user-circle" .}}< span > Users< / span > < / a >
< a class = "sidebar-link" href = "/admin/settings" > {{template "icon-settings" .}}< span > Settings< / span > < / a >
< a class = "sidebar-link" href = "/admin/storage" > {{template "icon-database" .}}< span > Storage< / span > < / a >
< a class = "sidebar-link is-active" href = "/admin/logs" > {{template "icon-database" .}}< span > Logs< / span > < / a >
< a class = "sidebar-link" href = "/admin/bans" > {{template "icon-settings" .}}< span > Bans< / span > < / a >
< / nav >
< hr class = "sidebar-sep" >
< nav class = "sidebar-nav" > < a class = "sidebar-link" href = "/app" > {{template "icon-home-simple" .}}< span > My Files< / span > < / a > < / nav >
< hr class = "sidebar-sep" >
< form class = "sidebar-logout" action = "/admin/logout" method = "post" >
< input type = "hidden" name = "csrf_token" value = "{{.CSRFToken}}" >
< button class = "button button-outline" type = "submit" > {{template "icon-log-out" .}}< span > Sign out< / span > < / button >
< / form >
< / aside >
< div class = "app-main" >
< div class = "admin-header" >
< div >
< p class = "kicker" > Operator console< / p >
< h1 id = "admin-logs-title" > {{.Data.PageTitle}}< / h1 >
< p class = "muted-copy" > Browse JSON log lines from the local log files.< / p >
< / div >
< / div >
< form class = "logs-filter-card" method = "get" action = "/admin/logs" >
< label > < span > Date< / span >
< select name = "date" >
< option value = "all" { { if eq . Data . Logs . Date " all " } } selected { { end } } > All dates< / option >
{{range .Data.Logs.Dates}}< option value = "{{.}}" { { if eq $ . Data . Logs . Date . } } selected { { end } } > {{.}}< / option > {{end}}
< / select >
< / label >
< label > < span > Severity< / span >
< select name = "severity" >
< option value = "" { { if eq . Data . Logs . Severity " " } } selected { { end } } > All< / option >
< option value = "dev" { { if eq . Data . Logs . Severity " dev " } } selected { { end } } > dev< / option >
< option value = "user_activity" { { if eq . Data . Logs . Severity " user_activity " } } selected { { end } } > user_activity< / option >
< option value = "warn" { { if eq . Data . Logs . Severity " warn " } } selected { { end } } > warn< / option >
< option value = "error" { { if eq . Data . Logs . Severity " error " } } selected { { end } } > error< / option >
< / select >
< / label >
< label > < span > Source< / span > < input name = "source" value = "{{.Data.Logs.Source}}" placeholder = "auth, admin, upload" > < / label >
< label > < span > Search< / span > < input name = "q" value = "{{.Data.Logs.Query}}" placeholder = "message, IP, path, user id" > < / label >
< label > < span > Sort< / span >
< select name = "sort" >
< option value = "desc" { { if eq . Data . Logs . Sort " desc " } } selected { { end } } > Newest first< / option >
< option value = "asc" { { if eq . Data . Logs . Sort " asc " } } selected { { end } } > Oldest first< / option >
< / select >
< / label >
2026-06-01 04:22:38 +03:00
< input type = "hidden" name = "per" value = "{{.Data.Logs.PerPage}}" >
2026-05-31 21:52:56 +03:00
< button class = "button button-primary" type = "submit" > Filter< / button >
< / form >
< div class = "card admin-table-card" >
< div class = "card-content" >
< div class = "table-header" >
< div >
< h2 > Log entries< / h2 >
2026-06-01 04:22:38 +03:00
< p > {{.Data.Logs.Total}} entries match these filters.< / p >
2026-05-31 21:52:56 +03:00
< / div >
< / div >
< div class = "admin-table-wrap" >
< table class = "admin-table logs-table" >
< thead >
< tr >
< th > Time< / th >
< th > Severity< / th >
< th > Source< / th >
< th > Code< / th >
< th > Message< / th >
< th > Actor/IP< / th >
< th > Route< / th >
< / tr >
< / thead >
< tbody >
{{range .Data.Logs.Entries}}
< tr >
< td > < span class = "log-time" > {{.Date}} {{.Time}}< / span > < / td >
< td > < span class = "badge" > {{.Severity}}< / span > < / td >
< td > {{.Source}}< / td >
< td > {{.Code}}< / td >
< td >
< strong > {{.Message}}< / strong >
{{if .Details}}< details > < summary > Details< / summary > < code > {{.Details}}< / code > < / details > {{end}}
< / td >
< td > {{if .UserID}}< code > {{.UserID}}< / code > {{end}}{{if .IP}}< br > < span > {{.IP}}< / span > {{end}}< / td >
< td > {{if .Method}}{{.Method}}{{end}} {{if .Path}}< code > {{.Path}}< / code > {{end}}{{if .Status}}< br > < span > Status {{.Status}}< / span > {{end}}< / td >
< / tr >
{{else}}
< tr > < td colspan = "7" > No log entries match those filters.< / td > < / tr >
{{end}}
< / tbody >
< / table >
< / div >
2026-06-01 04:22:38 +03:00
< div class = "pagination-bar" >
< nav class = "pagination" aria-label = "Pagination" >
{{if .Data.Logs.HasPrev}}< a class = "button button-outline button-sm" href = "{{.Data.Logs.PrevHref}}" > ← Prev< / a > {{else}}< span class = "button button-outline button-sm is-disabled" aria-disabled = "true" > ← Prev< / span > {{end}}
{{range .Data.Logs.PageLinks}}< a class = "button button-sm {{if .Active}}is-active{{else}}button-outline{{end}}" href = "{{.Href}}" > {{.Page}}< / a > {{end}}
{{if .Data.Logs.HasNext}}< a class = "button button-outline button-sm" href = "{{.Data.Logs.NextHref}}" > Next →< / a > {{else}}< span class = "button button-outline button-sm is-disabled" aria-disabled = "true" > Next →< / span > {{end}}
< / nav >
< label class = "per-page-control" >
< span > Per page< / span >
< select data-per-page = "logs" aria-label = "Items per page" >
{{range .Data.Logs.PerPageOptions}}< option value = "{{.}}" { { if eq . $ . Data . Logs . PerPage } } selected { { end } } > {{.}}< / option > {{end}}
< / select >
< / label >
< / div >
< p class = "pagination-summary" > Showing {{.Data.Logs.RangeFrom}}– {{.Data.Logs.RangeTo}} of {{.Data.Logs.Total}} · Page {{.Data.Logs.Page}} of {{.Data.Logs.TotalPages}}< / p >
2026-05-31 21:52:56 +03:00
< / div >
< / div >
< / div >
< / section >
{{end}}