diff --git a/cmd/verstak-server/server.go b/cmd/verstak-server/server.go index cbe6c5d..7559ffb 100644 --- a/cmd/verstak-server/server.go +++ b/cmd/verstak-server/server.go @@ -330,6 +330,7 @@ func (s *Server) routes() *http.ServeMux { mux.HandleFunc("/logout", s.handleUserWebLogout) mux.HandleFunc("/admin/login", s.handleAdminLogin) mux.HandleFunc("/admin/dashboard", s.handleAdminDashboard) + mux.HandleFunc("/admin/api/stats", s.handleAdminStats) mux.HandleFunc("/admin/", s.handleAdminAPI) mux.HandleFunc("/", s.handleNotFound) return mux @@ -1336,8 +1337,8 @@ a{color:#6366f1} h1{border-bottom:1px solid #2a2a3c;padding-bottom:12px} h2{margin-top:24px;font-size:16px} .stat{background:#1a1a28;border:1px solid #2a2a3c;padding:12px 16px;border-radius:8px;margin:8px 0} -.row{display:flex;gap:16px;flex-wrap:wrap} -.col{flex:1;min-width:300px} +.row{display:flex;gap:20px;flex-wrap:wrap;margin-top:8px} +.col{flex:1;min-width:280px;max-width:50%} table{width:100%;border-collapse:collapse;margin-top:8px} th,td{text-align:left;padding:8px 12px;border-bottom:1px solid #2a2a3c} th{font-size:12px;color:#888;text-transform:uppercase} @@ -1360,8 +1361,8 @@ form{margin-top:8px}

Verstak Sync Server

-
Устройств: %d
-
Операций: %d
+
Устройств: 0
+
Операций: 0
@@ -1376,6 +1377,10 @@ fetch('/admin/api/keys').then(r=>r.json()).then(keys=>{ keys.map(k=>''+k.name+''+k.api_key+''+ ''+ '').join('')+'' + document.getElementById('dev-count').textContent=keys.length +}) +fetch('/admin/api/stats').then(r=>r.json()).then(stats=>{ + document.getElementById('op-count').textContent=stats.ops||'0' }) function copyKey(key,btn){ navigator.clipboard.writeText(key).then(()=>{ @@ -1396,12 +1401,12 @@ function delKey(id){if(confirm('Удалить ключ?'))fetch('/admin/api/key

SMTP (для писем)

-
-
-
+
+
+
-
-
+
+
@@ -1409,10 +1414,19 @@ function delKey(id){if(confirm('Удалить ключ?'))fetch('/admin/api/key

Health check

-`, deviceCount, opsCount, smtpHost, smtpPort, smtpUser, smtpFrom, srvURL) +`) w.Write([]byte(html)) } +func (s *Server) handleAdminStats(w http.ResponseWriter, r *http.Request) { + if !s.requireAdmin(w, r) { + return + } + var opsCount int + s.db.QueryRow("SELECT COUNT(*) FROM server_ops").Scan(&opsCount) + jsonOK(w, map[string]int{"ops": opsCount}) +} + func (s *Server) handleAdminAPI(w http.ResponseWriter, r *http.Request) { if !s.requireAdmin(w, r) { return