1
0
Fork 0

fix: nodes no longer beg to be kept alive

This commit is contained in:
Arthur K. 2026-01-19 22:50:12 +03:00
parent 7c4154a459
commit a32b0f728e
Signed by: wzray
GPG key ID: B97F30FDC4636357
12 changed files with 146 additions and 62 deletions

View file

@ -0,0 +1,16 @@
package registry
import "git.wzray.com/homelab/hivemind/internal/types"
type Event int
const (
EventNodeJoin Event = iota
EventNodeLeave
EventSet
)
type RegistryEvent struct {
Event Event
Nodes map[string]types.Node
}

View file

@ -16,7 +16,7 @@ type Registry struct {
storage Storage
lock sync.RWMutex
self types.Node
observers []chan<- []types.Node
observers []chan<- RegistryEvent
}
func New(storage Storage, self types.Node) *Registry {
@ -47,42 +47,35 @@ func (r *Registry) snapshot() *storedConfig {
}
}
func (r *Registry) notify() {
nodes := r.Nodes()
func (r *Registry) notify(event RegistryEvent) {
for _, c := range r.observers {
c <- nodes
c <- event
}
}
func (r *Registry) AllNodes() []types.Node {
func (r *Registry) AllNodes() map[string]types.Node {
r.lock.RLock()
defer r.lock.RUnlock()
nodes := make([]types.Node, 0, len(r.nodes))
for _, n := range r.nodes {
nodes = append(nodes, n)
}
return nodes
return maps.Clone(r.nodes)
}
func (r *Registry) Nodes() []types.Node {
func (r *Registry) Nodes() map[string]types.Node {
nodes := r.AllNodes()
nodes = slices.DeleteFunc(nodes, func(n types.Node) bool {
return n.Hostname == r.self.Hostname
})
delete(nodes, r.self.Hostname)
return nodes
}
func (r *Registry) ByRole(role types.Role) []types.Node {
func (r *Registry) ByRole(role types.Role) map[string]types.Node {
r.lock.RLock()
defer r.lock.RUnlock()
o := make([]types.Node, 0, len(r.nodes))
for _, node := range r.nodes {
o := make(map[string]types.Node)
for name, node := range r.nodes {
if slices.Contains(node.Roles, role) && node.Hostname != r.self.Hostname {
o = append(o, node)
o[name] = node
}
}
return o
}
@ -96,12 +89,20 @@ func (r *Registry) AddNode(node types.Node) error {
if err := r.storage.Save(snapshot); err != nil {
return err
}
r.notify(RegistryEvent{
EventNodeJoin,
map[string]types.Node{
node.Hostname: node,
},
})
return nil
}
func (r *Registry) RemoveNode(nodeName string) error {
func (r *Registry) RemoveNode(node types.Node) error {
r.lock.Lock()
delete(r.nodes, nodeName)
delete(r.nodes, node.Hostname)
r.LastUpdate = time.Now()
snapshot := r.snapshot()
r.lock.Unlock()
@ -110,17 +111,19 @@ func (r *Registry) RemoveNode(nodeName string) error {
return err
}
r.notify()
r.notify(RegistryEvent{
EventNodeLeave,
map[string]types.Node{
node.Hostname: node,
},
})
return nil
}
func (r *Registry) Set(nodes []types.Node) error {
func (r *Registry) Set(nodes map[string]types.Node) error {
r.lock.Lock()
r.nodes = make(map[string]types.Node)
for _, n := range nodes {
r.nodes[n.Hostname] = n
}
r.nodes = maps.Clone(nodes)
snapshot := r.snapshot()
r.lock.Unlock()
@ -128,7 +131,10 @@ func (r *Registry) Set(nodes []types.Node) error {
return err
}
r.notify()
r.notify(RegistryEvent{
EventSet,
nodes,
})
return nil
}
@ -138,8 +144,8 @@ func (r *Registry) Exists(name string) bool {
return ok
}
func (r *Registry) OnChanged() <-chan []types.Node { // TODO: rename this
c := make(chan []types.Node, 1)
func (r *Registry) Subscribe() <-chan RegistryEvent { // TODO: rename this
c := make(chan RegistryEvent, 1)
r.observers = append(r.observers, c)
return c
}