package main import ( "context" "flag" "os" "os/signal" "git.faercol.me/faercol/public-ip-tracker/tracker/bot" "git.faercol.me/faercol/public-ip-tracker/tracker/config" "git.faercol.me/faercol/public-ip-tracker/tracker/logger" ) type cliArgs struct { configPath string } func parseArgs() *cliArgs { configPath := flag.String("config", "", "Path to the JSON configuration file") flag.Parse() return &cliArgs{ configPath: *configPath, } } func main() { args := parseArgs() mainCtx, cancel := context.WithCancel(context.Background()) conf, err := config.New(args.configPath) if err != nil { panic(err) } logger.Init(conf.Log.Level) logger.L.Infof("Intialized logger with level %v", conf.Log.Level) if conf.Hostname == "" { logger.L.Warn("Unspecified hostname, trying to get current hostname, this might not be reliable") conf.Hostname, err = os.Hostname() if err != nil { logger.L.Errorf("Failed to get hostname, using a default value: %s", err.Error()) conf.Hostname = "default" } } logger.L.Debug("Initializing notification bot") notifBot, err := bot.New(mainCtx, conf) if err != nil { logger.L.Fatalf("Failed to create notification bot: %s", err.Error()) } logger.L.Debug("Sending initialization message to Telegram") if err := notifBot.SendInitMessage(); err != nil { logger.L.Fatalf("Failed to send an initialization message: %s", err.Error()) } logger.L.Debug("Starting IP monitoring") go notifBot.Run() c := make(chan os.Signal, 1) signal.Notify(c, os.Interrupt) logger.L.Info("Public IP monitoring service is operational") outerloop: for { select { case <-c: logger.L.Info("Stopping IP monitoring service") cancel() break outerloop case err := <-notifBot.ErrChan(): logger.L.Error(err.Error()) case <-notifBot.Exit(): logger.L.Fatal("Unexpected exit from the monitoring bot") } } logger.L.Debug("Waiting for all services to shut down") <-notifBot.Exit() logger.L.Info("Public IP monitoring service successfully stopped") os.Exit(0) }