package worker import ( "context" "io" "log/slog" "net/http" "git.lastassault.de/speatzle/morffix/rpc" "os" "os/signal" "time" "git.lastassault.de/speatzle/morffix/config" "git.lastassault.de/speatzle/morffix/constants" "github.com/google/uuid" "nhooyr.io/websocket" ) var conf config.Config var rpcServer = rpc.NewServer() func Start(_conf config.Config) { conf = _conf ctx, cancel := context.WithCancel(context.Background()) uuid := uuid.New() sigs := make(chan os.Signal, 1) signal.Notify(sigs, os.Interrupt) exit := false go func() { <-sigs slog.InfoContext(ctx, "Got Signal...") exit = true cancel() }() for { if exit { slog.InfoContext(ctx, "Done") return } connectToServer(ctx, uuid) if exit { slog.InfoContext(ctx, "Done") return } time.Sleep(time.Second) } } func connectToServer(ctx context.Context, uuid uuid.UUID) { slog.InfoContext(ctx, "Connecting to Server...", "Address", conf.Worker.Address) headers := http.Header{} headers.Add(constants.SHARED_SECRET_HEADER, conf.SharedSecret) headers.Add(constants.NAME_HEADER, conf.Worker.Name) headers.Add(constants.UUID_HEADER, uuid.String()) headers.Add(constants.WORKER_VERSION_HEADER, constants.WORKER_VERSION) c, res, err := websocket.Dial(ctx, conf.Worker.Address, &websocket.DialOptions{ HTTPHeader: headers, }) if err != nil { if res != nil { b, _ := io.ReadAll(res.Body) slog.ErrorContext(ctx, "Error Connecting to Server", "err", err, "code", res.Status, "body", b) } else { slog.ErrorContext(ctx, "Error Connecting to Server", "err", err) } return } slog.InfoContext(ctx, "Waiting for Messages") for { err = readMessage(ctx, c) if websocket.CloseStatus(err) == websocket.StatusNormalClosure || websocket.CloseStatus(err) == websocket.StatusAbnormalClosure || websocket.CloseStatus(err) == websocket.StatusGoingAway { slog.InfoContext(ctx, "Websocket Closed") return } if err != nil { slog.ErrorContext(ctx, "Error Reading Websocket Message", "err", err) return } } } func readMessage(ctx context.Context, c *websocket.Conn) error { t, data, err := c.Read(ctx) if err != nil { return err } slog.InfoContext(ctx, "Got Websocket Message", "type", t.String(), "data", data) rpcServer.HandleMessage(ctx, c, data) return nil }