feat: user roles - admins and users limited to the machines given to them, user editor with machines, password sign-in and its lock; direct address without Cloudflare as the agents' fallback and in the installer; version 0.1.2

This commit is contained in:
redtea committed 2026-10-15 10:56:19 +03:00
1 parent 36dc12b69d
commit 021da93229
29 files changed
+844 -97

No files matched your search

+9 -2
View File
@@ -30,8 +30,13 @@ type wsLink struct {
subs map[string]chan wsIn
asked map[string]bool // sessions whose input was asked for
done chan struct{}
stop context.CancelFunc
}
// close drops the link: the agent then connects again, to the address in
// use by then.
func (l *wsLink) close() { l.stop() }
// wsIn is what the server sent for a session: its input, or that it is over.
type wsIn struct {
frames []proto.InFrame
@@ -95,7 +100,7 @@ func (l *wsLink) deliver(sid string, in wsIn) {
// runWS holds the WebSocket until it ends, dispatching what comes on it.
func (a *Agent) runWS(ctx context.Context) error {
u := a.cfg.Host + "/api/agent/ws"
u := a.host() + "/api/agent/ws"
u = "ws" + strings.TrimPrefix(u, "http")
hdr := http.Header{}
hdr.Set("X-Agent-Id", a.state.AgentID)
@@ -116,7 +121,7 @@ func (a *Agent) runWS(ctx context.Context) error {
}
c.SetReadLimit(8 << 20)
lctx, lcancel := context.WithCancel(ctx)
l := &wsLink{c: c, ctx: lctx, subs: map[string]chan wsIn{}, done: make(chan struct{})}
l := &wsLink{c: c, ctx: lctx, subs: map[string]chan wsIn{}, done: make(chan struct{}), stop: lcancel}
a.link.Store(l)
defer func() {
a.link.CompareAndSwap(l, nil)
@@ -125,6 +130,7 @@ func (a *Agent) runWS(ctx context.Context) error {
c.CloseNow()
}()
log.Printf("connected by websocket")
a.reached()
go func() {
t := time.NewTicker(wsPing)
defer t.Stop()
@@ -159,6 +165,7 @@ func (a *Agent) runWS(ctx context.Context) error {
}
case "cfg":
a.applyTunnelAddr(ctx, m.Tunnel)
a.learnFallback(m.Fallback)
a.applyTransport(m.Transport)
if a.mode() == proto.TransportLP {
return errors.New("set to long polling")