rmm2/agent/collector/opnsense.go
cynfo3000 e74cdce0ba Agent-Updater, Multi-Plattform Firmware, Frontend Firmware-Seite, Agent-Tab, Zertifikate-Redesign
Updater:
- Separater Go-Daemon (rmm-updater) als eigener rc.d Service
- Pollt alle 60s: Firmware vorhanden + Hash unterschiedlich + Flag gesetzt
- Download -> SHA256 Verify -> Agent Stop -> Replace -> Agent Start
- Automatisches Rollback bei Fehler
- Deployed und getestet auf allen 3 Firewalls (.1, .19, .33)

Backend:
- Firmware-DB multi-plattform (freebsd/linux/windows)
- update_requested Flag pro Agent in agents Tabelle
- Heartbeat-Response liefert update_available wenn Flag gesetzt
- Neue Endpoints: request-update, request-update-all, firmware/download
- Auth: JWT + CombinedAuth Middleware (API-Key OR JWT)
- Customers CRUD + Agent-Zuordnung
- Users CRUD + Passwort-Aenderung

Frontend:
- Firmware-Seite: Multi-Plattform Upload, Agent-Liste mit Update-Trigger
- Agent-Tab im AgentPanel: Update-Button, nuetzliche Befehle, Agent-Info
- Zertifikate-Tab redesigned: Karten-Layout mit Restlaufzeit und Farbbalken
- Sidebar: Firmware-Eintrag hinzugefuegt

Plugin:
- install.sh erweitert: Installiert Agent + Updater + rc.d Services
- rmm_updater rc.d Service

README:
- Architektur-Diagramm erweitert (Frontend + Updater)
- Auth, Customers, Users, Firmware API dokumentiert
- Updater-Flow dokumentiert
- Frontend-Seiten und Deploy beschrieben
- DB-Schema aktualisiert (neue Tabellen)
- Dateistruktur erweitert (updater/, frontend/, firmware.go, auth.go)
2026-02-28 22:43:03 +01:00

62 lines
1.2 KiB
Go

package collector
import (
"os/exec"
"strconv"
"strings"
"time"
)
func CollectOPNsenseVersion() string {
out, err := exec.Command("/usr/local/sbin/opnsense-version").Output()
if err != nil {
return ""
}
// Format: "OPNsense 24.1.1_1" - alles nach erstem Leerzeichen
s := strings.TrimSpace(string(out))
return s
}
func CollectFreeBSDVersion() string {
out, err := exec.Command("/bin/freebsd-version").Output()
if err != nil {
return sysctlGet("kern.osrelease")
}
return strings.TrimSpace(string(out))
}
func CollectHostname() string {
return sysctlGet("kern.hostname")
}
func CollectUptime() int64 {
// kern.boottime: { sec = 1706000000, usec = 0 } ... oder "sec = 1706000000"
out := sysctlGet("kern.boottime")
if out == "" {
return 0
}
// Parse "{ sec = TIMESTAMP, usec = ... }"
idx := strings.Index(out, "sec = ")
if idx == -1 {
return 0
}
numStr := out[idx+6:]
if commaIdx := strings.IndexAny(numStr, ", }"); commaIdx != -1 {
numStr = numStr[:commaIdx]
}
numStr = strings.TrimSpace(numStr)
bootTime, err := strconv.ParseInt(numStr, 10, 64)
if err != nil {
return 0
}
uptime := time.Now().Unix() - bootTime
if uptime < 0 {
return 0
}
return uptime
}