Files
mocksnow/main.go
2025-03-21 19:49:41 +11:00

233 lines
6.5 KiB
Go

package main
import (
"fmt"
"os"
"runtime"
"time"
"wnzl-snow/db"
"wnzl-snow/internal/settings"
utils "wnzl-snow/internal/utils"
"wnzl-snow/log"
"wnzl-snow/server"
"wnzl-snow/server/router"
"github.com/go-co-op/gocron/v2"
"github.com/joho/godotenv"
)
var (
bindDisableTls bool
sha1ver string // sha1 revision used to build the program
buildTime string // when the executable was built
cronFrequency time.Duration
cronInvFrequency time.Duration
encryptionKey = []byte("5L1l3B5KvwOCzUHMAlCgsgUTRAYMfSpa")
)
func main() {
// Load data from environment file
envFilename := utils.GetFilePath(".env")
err := godotenv.Load(envFilename)
if err != nil {
panic("Error loading .env file")
}
logger := log.New(
log.GetLevel(),
log.GetOutput(),
)
//ctx, cancel := context.WithCancel(context.Background())
// Configure database
database, err := db.New(logger, utils.GetFilePath("db.sqlite3"))
if err != nil {
logger.Error("Failed to create database", "error", err)
os.Exit(1)
}
defer database.Close()
//defer database.DB().Close()
if err = db.Migrate(database); err != nil {
logger.Error("failed to migrate database", "error", err)
os.Exit(1)
}
// Load settings from yaml
settingsFile := os.Getenv("SETTINGS_FILE")
if settingsFile == "" {
settingsFile = "settings.yaml"
}
// TODO - how to pass this to the other packages that will need this info?
s := settings.New(logger, settingsFile)
err = s.ReadYMLSettings()
//s, err := settings.ReadYMLSettings(logger, settingsFile)
if err != nil {
logger.Error("failed to open yaml settings file", "error", err, "filename", settingsFile)
//os.Exit(1)
} else {
logger.Debug("Loaded yaml settings", "contents", s)
}
// Determine bind IP
bindIP := os.Getenv("BIND_IP")
if bindIP == "" {
bindIP = utils.GetOutboundIP().String()
}
// Determine bind port
bindPort := os.Getenv("BIND_PORT")
if bindPort == "" {
bindPort = "9443"
}
bindAddress := fmt.Sprint(bindIP, ":", bindPort)
//logger.Info("Will listen on address", "ip", bindIP, "port", bindPort)
// Determine bind disable TLS
bindDisableTlsEnv := os.Getenv("BIND_DISABLE_TLS")
if bindDisableTlsEnv == "true" {
bindDisableTls = true
}
// Get file names for TLS cert/key
tlsCertFilename := os.Getenv("TLS_CERT_FILE")
if tlsCertFilename != "" {
tlsCertFilename = utils.GetFilePath(tlsCertFilename)
} else {
tlsCertFilename = "./cert.pem"
}
tlsKeyFilename := os.Getenv("TLS_KEY_FILE")
if tlsKeyFilename != "" {
tlsKeyFilename = utils.GetFilePath(tlsKeyFilename)
} else {
tlsKeyFilename = "./privkey.pem"
}
// Generate certificate if required
if !(utils.FileExists(tlsCertFilename) && utils.FileExists(tlsKeyFilename)) {
logger.Warn("Specified TLS certificate or private key do not exist", "certificate", tlsCertFilename, "tls-key", tlsKeyFilename)
utils.GenerateCerts(tlsCertFilename, tlsKeyFilename)
}
// Prepare the task scheduler
c, err := gocron.NewScheduler()
if err != nil {
logger.Error("failed to create scheduler", "error", err)
os.Exit(1)
}
/*
// Load vcenter credentials from .env
a := secrets.New(logger, encryptionKey)
vcEp := os.Getenv("VCENTER_PASSWORD")
if len(vcEp) == 0 {
logger.Error("No vcenter password configured")
os.Exit(1)
}
vcPass, err := a.Decrypt(vcEp)
if err != nil {
logger.Error("failed to decrypt vcenter credentials. Assuming un-encrypted", "error", err)
vcPass = []byte(vcEp)
//os.Exit(1)
}
creds := vcenter.VcenterLogin{
//insecureString := os.Getenv("VCENTER_INSECURE")
Username: os.Getenv("VCENTER_USERNAME"),
Password: string(vcPass),
}
// Prepare the task scheduler
c, err := gocron.NewScheduler()
if err != nil {
logger.Error("failed to create scheduler", "error", err)
os.Exit(1)
}
// Pass useful information to the cron jobs
ct := &tasks.CronTask{
Logger: logger,
Database: database,
Settings: s,
VcCreds: &creds,
}
cronFrequencyString := os.Getenv("VCENTER_EVENT_POLLING_SECONDS")
if cronFrequencyString != "" {
cronFrequency, err = time.ParseDuration(cronFrequencyString)
if err != nil {
slog.Error("Can't convert VCENTER_EVENT_POLLING_SECONDS value to time duration. Defaulting to 60s", "value", cronFrequencyString, "error", err)
cronFrequency = time.Second * 60
}
} else {
cronFrequency = time.Second * 60
}
logger.Debug("Setting VM event polling cronjob frequency to", "frequency", cronFrequency)
cronInventoryFrequencyString := os.Getenv("VCENTER_INVENTORY_POLLING_SECONDS")
if cronInventoryFrequencyString != "" {
cronInvFrequency, err = time.ParseDuration(cronInventoryFrequencyString)
if err != nil {
slog.Error("Can't convert VCENTER_INVENTORY_POLLING_SECONDS value to time duration. Defaulting to 7200", "value", cronInventoryFrequencyString, "error", err)
cronInvFrequency = time.Second * 7200
}
} else {
cronInvFrequency = time.Second * 7200
}
logger.Debug("Setting VM inventory polling cronjob frequency to", "frequency", cronInvFrequency)
// start background processing for events stored in events table
startsAt := time.Now().Add(time.Second * 10)
job, err := c.NewJob(
gocron.DurationJob(cronFrequency),
gocron.NewTask(func() {
ct.RunVmCheck(ctx, logger)
}), gocron.WithSingletonMode(gocron.LimitModeReschedule),
gocron.WithStartAt(gocron.WithStartDateTime(startsAt)),
)
if err != nil {
logger.Error("failed to start event processing cron job", "error", err)
os.Exit(1)
}
logger.Debug("Created event processing cron job", "job", job.ID(), "starting_at", startsAt)
// start background checks of vcenter inventory
startsAt2 := time.Now().Add(cronInvFrequency)
job2, err := c.NewJob(
gocron.DurationJob(cronInvFrequency),
gocron.NewTask(func() {
ct.RunVcenterPoll(ctx, logger)
}), gocron.WithSingletonMode(gocron.LimitModeReschedule),
gocron.WithStartAt(gocron.WithStartDateTime(startsAt2)),
)
if err != nil {
logger.Error("failed to start vcenter inventory cron job", "error", err)
os.Exit(1)
}
logger.Debug("Created vcenter inventory cron job", "job", job2.ID(), "starting_at", startsAt2)
// start cron scheduler
c.Start()
*/
// Start server
r := router.New(logger, database, buildTime, sha1ver, runtime.Version(), s)
svr := server.New(
logger,
c,
//cancel,
bindAddress,
server.WithRouter(r),
server.SetTls(bindDisableTls),
server.SetCertificate(tlsCertFilename),
server.SetPrivateKey(tlsKeyFilename),
)
//logger.Debug("Server configured", "object", svr)
svr.StartAndWait()
os.Exit(0)
}