1
0
Fork 0

refactor: move http api to a new transport layer

This commit is contained in:
Arthur K. 2026-01-23 09:56:01 +03:00
parent 476c4b056f
commit 0448f66ab2
Signed by: wzray
GPG key ID: B97F30FDC4636357
41 changed files with 822 additions and 390 deletions

View file

@ -4,23 +4,24 @@ import (
"context"
"sync"
"git.wzray.com/homelab/hivemind/internal/app"
"git.wzray.com/homelab/hivemind/internal/config"
"git.wzray.com/homelab/hivemind/internal/roles"
"git.wzray.com/homelab/hivemind/internal/state"
"git.wzray.com/homelab/hivemind/internal/transport"
"git.wzray.com/homelab/hivemind/internal/transport/master"
"git.wzray.com/homelab/hivemind/internal/types"
"git.wzray.com/homelab/hivemind/internal/web/client"
"github.com/rs/zerolog/log"
)
type Role struct {
state *state.RuntimeState
state *app.State
config config.MasterConfig
tasksGroup sync.WaitGroup
observer *observer
roles.BaseRole
}
func New(state *state.RuntimeState, config config.MasterConfig) *Role {
func New(state *app.State, config config.MasterConfig) *Role {
return &Role{
state: state,
config: config,
@ -50,13 +51,34 @@ func (r *Role) OnShutdown() error {
return nil
}
func (r *Role) notify(path types.Path, v any) {
for _, n := range r.state.Registry.ByRole(types.MasterRole) {
addr := n.Endpoint
r.tasksGroup.Go(func() {
client.Post[any](addr, path, v)
})
}
func (c *Role) RegisterHandlers(r transport.Registrator) {
master.Register(r, c)
}
func (r *Role) Heartbeat(node types.Node) (types.Nodes, error) {
return r.onKeepAlive(node, true)
}
func (r *Role) Join(node types.Node) (types.Nodes, error) {
return r.onJoin(node, true)
}
func (r *Role) Leave(node types.Node) error {
_, err := r.onLeave(node, true)
return err
}
func (r *Role) EventHeartbeat(node types.Node) (types.Nodes, error) {
return r.onKeepAlive(node, false)
}
func (r *Role) EventJoin(node types.Node) (types.Nodes, error) {
return r.onJoin(node, false)
}
func (r *Role) EventLeave(node types.Node) error {
_, err := r.onLeave(node, false)
return err
}
func (r *Role) onJoin(node types.Node, notify bool) (map[string]types.Node, error) {
@ -65,7 +87,7 @@ func (r *Role) onJoin(node types.Node, notify bool) (map[string]types.Node, erro
}
if notify {
r.notify(types.PathMasterEventJoin, node)
propagate(r, noReturn(r.state.Clients.Master.EventJoin), node)
}
return r.state.Registry.AllNodes(), nil
@ -77,7 +99,7 @@ func (r *Role) onLeave(node types.Node, notify bool) (bool, error) {
}
if notify {
r.notify(types.PathMasterEventLeave, node)
propagate(r, r.state.Clients.Master.EventLeave, node)
}
return true, nil
@ -94,7 +116,7 @@ func (r *Role) onKeepAlive(node types.Node, notify bool) (map[string]types.Node,
}
if notify {
r.notify(types.PathMasterEventKeepalive, node)
propagate(r, noReturn(r.state.Clients.Master.EventHeartbeat), node)
}
return r.state.Registry.AllNodes(), nil
@ -106,11 +128,18 @@ func eventFunc[R any](fn func(types.Node, bool) (R, error), notify bool) func(ty
}
}
func (c *Role) RegisterHandlers(r types.Registrator) {
r.Register(types.PostEndpoint(types.PathMasterKeepalive, eventFunc(c.onKeepAlive, true)))
r.Register(types.PostEndpoint(types.PathMasterEventKeepalive, eventFunc(c.onKeepAlive, false)))
r.Register(types.PostEndpoint(types.PathMasterJoin, eventFunc(c.onJoin, true)))
r.Register(types.PostEndpoint(types.PathMasterLeave, eventFunc(c.onLeave, true)))
r.Register(types.PostEndpoint(types.PathMasterEventJoin, eventFunc(c.onJoin, false)))
r.Register(types.PostEndpoint(types.PathMasterEventLeave, eventFunc(c.onLeave, false)))
func noReturn[T, V any](fn func(string, T) (V, error)) func(string, T) error {
return func(s string, t T) error {
_, err := fn(s, t)
return err
}
}
func propagate[T any](r *Role, handler func(string, T) error, v T) {
for _, n := range r.state.Registry.ByRole(types.MasterRole) {
addr := n.Endpoint
r.tasksGroup.Go(func() {
handler(addr, v)
})
}
}