mirror of
https://github.com/netbirdio/netbird.git
synced 2026-09-25 08:09:07 +02:00
[client] UI refactor (#6069)
Refactor UI --------- Co-authored-by: Eduard Gert <kontakt@eduardgert.de> Co-authored-by: braginini <bangvalo@gmail.com> Co-authored-by: Pascal Fischer <32096965+pascal-fischer@users.noreply.github.com> Co-authored-by: Claude <noreply@anthropic.com> Co-authored-by: riccardom <riccardomanfrin@gmail.com>
This commit is contained in:
co-authored by
Eduard Gert
braginini
Pascal Fischer
Claude
riccardom
parent
679c7182a4
commit
8b7ce337d8
@@ -0,0 +1,97 @@
|
||||
//go:build !android && !ios && !freebsd && !js
|
||||
|
||||
// Package updater holds the auto-update domain: the typed State, the
|
||||
// daemon-SystemEvent metadata schema, and the Holder that caches the latest
|
||||
// state and broadcasts changes. No Wails dependency.
|
||||
package updater
|
||||
|
||||
import (
|
||||
"sync"
|
||||
|
||||
log "github.com/sirupsen/logrus"
|
||||
|
||||
"github.com/netbirdio/netbird/client/proto"
|
||||
)
|
||||
|
||||
// EventStateChanged carries the full State snapshot as payload.
|
||||
const EventStateChanged = "netbird:update:state"
|
||||
|
||||
// State is the typed snapshot of the daemon's update situation. Installing is
|
||||
// driven only by the daemon's progress_window:show event; a UI-side
|
||||
// Update.Trigger() does not flip it.
|
||||
type State struct {
|
||||
Available bool `json:"available"`
|
||||
Version string `json:"version"`
|
||||
Enforced bool `json:"enforced"`
|
||||
Installing bool `json:"installing"`
|
||||
}
|
||||
|
||||
// Emitter is the broadcast dependency Holder needs; the Wails app.Event
|
||||
// processor satisfies it.
|
||||
type Emitter interface {
|
||||
Emit(name string, data ...any) bool
|
||||
}
|
||||
|
||||
// Holder caches the latest update State and broadcasts changes.
|
||||
type Holder struct {
|
||||
emitter Emitter
|
||||
|
||||
mu sync.Mutex
|
||||
state State
|
||||
}
|
||||
|
||||
// NewHolder constructs an empty-state Holder. A nil emitter skips the broadcast.
|
||||
func NewHolder(emitter Emitter) *Holder {
|
||||
return &Holder{emitter: emitter}
|
||||
}
|
||||
|
||||
// Get returns a copy of the cached State.
|
||||
func (h *Holder) Get() State {
|
||||
h.mu.Lock()
|
||||
defer h.mu.Unlock()
|
||||
return h.state
|
||||
}
|
||||
|
||||
// OnSystemEvent folds update-related metadata into the cached state, emitting
|
||||
// EventStateChanged only on an actual change so repeated daemon snapshots
|
||||
// don't produce redundant pushes.
|
||||
func (h *Holder) OnSystemEvent(ev *proto.SystemEvent) {
|
||||
md := ev.GetMetadata()
|
||||
if len(md) == 0 {
|
||||
return
|
||||
}
|
||||
|
||||
h.mu.Lock()
|
||||
changed := false
|
||||
if v, ok := md["new_version_available"]; ok {
|
||||
_, enforced := md["enforced"]
|
||||
if !h.state.Available || h.state.Version != v || h.state.Enforced != enforced {
|
||||
h.state.Available = true
|
||||
h.state.Version = v
|
||||
h.state.Enforced = enforced
|
||||
changed = true
|
||||
}
|
||||
}
|
||||
if md["progress_window"] == "show" {
|
||||
if !h.state.Installing {
|
||||
h.state.Installing = true
|
||||
changed = true
|
||||
}
|
||||
if v, ok := md["version"]; ok && v != "" && h.state.Version != v {
|
||||
h.state.Version = v
|
||||
h.state.Available = true
|
||||
changed = true
|
||||
}
|
||||
}
|
||||
snap := h.state
|
||||
h.mu.Unlock()
|
||||
|
||||
if !changed {
|
||||
return
|
||||
}
|
||||
log.Infof("update state: available=%v version=%q enforced=%v installing=%v",
|
||||
snap.Available, snap.Version, snap.Enforced, snap.Installing)
|
||||
if h.emitter != nil {
|
||||
h.emitter.Emit(EventStateChanged, snap)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user