oneuptime/InfrastructureAgent/main.go

201 lines
4.9 KiB
Go

package main
import (
"flag"
"fmt"
"log/slog"
"os"
"github.com/gookit/config/v2"
"github.com/kardianos/service"
)
type program struct {
exit chan struct{}
agent *Agent
config *ConfigFile
}
func (p *program) Start(s service.Service) error {
if service.Interactive() {
slog.Info("Running in terminal.")
} else {
slog.Info("Running under service manager.")
}
p.exit = make(chan struct{})
// Start should not block. Do the actual work async.
go p.run()
return nil
}
func (p *program) run() {
p.agent = NewAgent(p.config.SecretKey, p.config.OneUptimeURL)
p.agent.Start()
if service.Interactive() {
slog.Info("Running in terminal.")
NewShutdownHook().Close(func() {
slog.Info("Service Exiting...")
p.agent.Close()
})
} else {
slog.Info("Running under service manager.")
for {
select {
case _, ok := <-p.exit:
if !ok {
slog.Info("Service Exiting...")
p.agent.Close()
return
}
}
}
}
}
func (p *program) Stop(s service.Service) error {
close(p.exit)
return nil
}
func main() {
// Set up the configuration
config.WithOptions(config.WithTagName("json"))
cfg := newConfigFile()
// Set up the service
svcConfig := &service.Config{
Name: "oneuptime-infrastructure-agent",
DisplayName: "OneUptime Infrastructure Agent",
Description: "The OneUptime Infrastructure Agent is a lightweight, open-source agent that collects system metrics and sends them to the OneUptime platform. It is designed to be easy to configure and use, and to be extensible.",
Arguments: []string{"run"},
}
// Set up the program
prg := &program{
config: cfg,
}
// Create the service
s, err := service.New(prg, svcConfig)
if err != nil {
slog.Error(err.Error())
os.Exit(2)
}
if err != nil {
slog.Error(err.Error())
os.Exit(2)
}
if len(os.Args) > 1 {
cmd := os.Args[1]
switch cmd {
case "configure":
installFlags := flag.NewFlagSet("configure", flag.ExitOnError)
secretKey := installFlags.String("secret-key", "", "Secret key (required)")
oneuptimeURL := installFlags.String("oneuptime-url", "", "Oneuptime endpoint root URL (required)")
err := installFlags.Parse(os.Args[2:])
if err != nil {
slog.Error(err.Error())
os.Exit(2)
}
prg.config.SecretKey = *secretKey
prg.config.OneUptimeURL = *oneuptimeURL
if prg.config.SecretKey == "" || prg.config.OneUptimeURL == "" {
slog.Error("The --secret-key and --oneuptime-url flags are required for the 'configure' command")
os.Exit(2)
}
// save configuration
err = prg.config.save(prg.config.SecretKey, prg.config.OneUptimeURL)
if err != nil {
slog.Error(err.Error())
os.Exit(2)
}
// Install the service
if err := s.Install(); err != nil {
slog.Error("Failed to configure service: ", err)
os.Exit(2)
}
fmt.Println("Service installed. Run the service using 'oneuptime-infrastructure-agent start'")
case "start":
err := prg.config.loadConfig()
if os.IsNotExist(err) {
slog.Error("Service configuration not found. Please run 'oneuptime-infrastructure-agent configure' to configure the service.")
os.Exit(2)
}
if err != nil {
slog.Error(err.Error())
os.Exit(2)
}
if err != nil || prg.config.SecretKey == "" || prg.config.OneUptimeURL == "" {
slog.Error("Service configuration not found or is incomplete. Please run 'oneuptime-infrastructure-agent configure' to configure the service.")
os.Exit(2)
}
err = s.Start()
if err != nil {
slog.Error(err.Error())
os.Exit(1)
}
slog.Info("OneUptime Infrastructure Agent Started")
case "run":
err := prg.config.loadConfig()
if os.IsNotExist(err) {
slog.Error("Service configuration not found. Please run 'oneuptime-infrastructure-agent configure' to configure the service.")
os.Exit(2)
}
if err != nil {
slog.Error(err.Error())
os.Exit(2)
}
if err != nil || prg.config.SecretKey == "" || prg.config.OneUptimeURL == "" {
slog.Error("Service configuration not found or is incomplete. Please run 'oneuptime-infrastructure-agent configure' to configure the service.")
os.Exit(2)
}
err = s.Run()
if err != nil {
slog.Error(err.Error())
os.Exit(1)
}
case "uninstall", "stop", "restart":
err := service.Control(s, cmd)
if err != nil {
slog.Error(err.Error())
os.Exit(2)
}
if cmd == "uninstall" {
// remove configuration file
err := prg.config.removeConfigFile()
if err != nil {
slog.Error(err.Error())
os.Exit(2)
}
slog.Info("Service Uninstalled")
}
if cmd == "stop" {
slog.Info("Service Stopped")
}
if cmd == "restart" {
slog.Info("Service Restarted")
}
// add help command
case "help":
fmt.Println("Usage: oneuptime-infrastructure-agent configure | uninstall | start | stop | restart")
default:
slog.Error("Invalid command")
os.Exit(2)
}
} else {
fmt.Println("Usage: oneuptime-infrastructure-agent configure | uninstall | start | stop | restart")
}
}