sfcs/client/Start.go

95 lines
2.3 KiB
Go
Raw Permalink Normal View History

2025-02-03 21:17:49 +01:00
package client
import (
"log"
"os"
"os/signal"
"strconv"
"time"
"github.com/gorilla/websocket"
"github.com/inhies/go-bytesize"
"github.com/mackerelio/go-osstat/memory"
"github.com/shirou/gopsutil/cpu"
2025-02-03 21:17:49 +01:00
)
func (client *Client) Start() {
// Setup interrupt handling
2025-02-03 21:17:49 +01:00
interrupt := make(chan os.Signal, 1)
signal.Notify(interrupt, os.Interrupt)
// Connect to the server
err := client.connectToServer()
2025-02-03 21:17:49 +01:00
if err != nil {
log.Fatal("ERROR: Failed connecting to server - ", err)
2025-02-03 21:17:49 +01:00
}
defer client.conn.Close()
2025-02-03 21:17:49 +01:00
// Agent => Manager:
// - register: register an agent with the manager
// - update: agents sends CPU and Mem metrics (does this every second)
// - solution: solution of a task given by the manager
// - deregister: deregister an agent from the manager
// Register
// One-time at the start
// Fetch the hostname
hostname, err := os.Hostname()
if err != nil {
log.Fatal("ERROR: Failed to register - cannot get hostname - ", err)
}
// Fetch the number of logical cores
cpustats, err := cpu.Counts(true)
if err != nil {
log.Fatal("ERROR: Failed to register - unable to fetch number of cores - ", err)
}
// Fetch memory stats in bytes
mem, err := memory.Get()
if err != nil {
log.Println("ERROR: Failed to register - fetching memory info - ", err)
}
// Use the ByteSize package to allow for memory calculations
b := bytesize.New(float64(mem.Total))
// Register this agent with the scheduler
client.writeToServer("register;" + hostname + ";" + strconv.Itoa(cpustats) + ";" + b.String())
2025-02-03 21:17:49 +01:00
// Setup updater logic
// Runs continuesly in the background
go client.statusUpdater()
// Start handler for incoming messages
done := make(chan struct{})
go client.handleIncoming(done)
2025-02-03 21:17:49 +01:00
for {
select {
case <-done:
return
case <-interrupt:
log.Println("Interrupt received -- Stopping")
// Dereg the agent before dying off
client.writeToServer("deregister;" + hostname)
2025-02-03 21:17:49 +01:00
// Cleanly close the connection by sending a close message and then
// waiting (with timeout) for the server to close the connection.
err := client.conn.WriteMessage(websocket.CloseMessage, websocket.FormatCloseMessage(websocket.CloseNormalClosure, ""))
2025-02-03 21:17:49 +01:00
if err != nil {
log.Println("ERROR: Close connection - ", err)
2025-02-03 21:17:49 +01:00
return
}
select {
case <-done:
case <-time.After(time.Second):
}
return
}
}
}