// Command exploredns-receiver stores usage webhooks posted by the // ExploreDNS API server in MySQL or SQLite. // // Configuration (environment): // // RECEIVER_ADDR listen address (default ":8080") // RECEIVER_MYSQL_DSN go-sql-driver DSN; when set, events go to MySQL // RECEIVER_SQLITE_PATH SQLite fallback path (default "data/exploredns-receiver.db") // RECEIVER_INGEST_TOKEN bearer token required on POST /webhook (open when unset) // RECEIVER_ADMIN_USER basic-auth username for /admin (default "admin") // RECEIVER_ADMIN_PASSWORD basic-auth password for /admin (required) package main import ( "fmt" "log" "os" "os/signal" "syscall" "time" "gitea.hansenits.com.au/hits/ExploreDNS/internal/receiver/server" "gitea.hansenits.com.au/hits/ExploreDNS/internal/receiver/store" ) // version is stamped at build time via -ldflags "-X main.version=...". var version = "dev" func main() { addr := envOr("RECEIVER_ADDR", ":8080") adminPass := os.Getenv("RECEIVER_ADMIN_PASSWORD") if adminPass == "" { fmt.Fprintln(os.Stderr, "Error: RECEIVER_ADMIN_PASSWORD is not set; refusing to start with an unprotected admin interface") os.Exit(1) } var ( st *store.Store backend string err error ) if dsn := os.Getenv("RECEIVER_MYSQL_DSN"); dsn != "" { st, err = store.OpenMySQL(dsn) backend = "mysql " + store.RedactMySQLDSN(dsn) } else { path := envOr("RECEIVER_SQLITE_PATH", "data/exploredns-receiver.db") st, err = store.OpenSQLite(path) backend = "sqlite " + path } if err != nil { fmt.Fprintf(os.Stderr, "Error: %v\n", err) os.Exit(1) } srv := server.New(addr, st) srv.SetVersion(version) srv.SetIngestToken(os.Getenv("RECEIVER_INGEST_TOKEN")) srv.SetAdminAuth(envOr("RECEIVER_ADMIN_USER", "admin"), adminPass) if err := srv.Start(); err != nil { fmt.Fprintf(os.Stderr, "Error: %v\n", err) os.Exit(1) } log.Printf("ExploreDNS receiver %s listening on %s, storing to %s", version, srv.Addr(), backend) quit := make(chan os.Signal, 1) signal.Notify(quit, syscall.SIGINT, syscall.SIGTERM) <-quit log.Println("Shutting down...") if err := srv.Shutdown(15 * time.Second); err != nil { log.Printf("Shutdown error: %v", err) } if err := st.Close(); err != nil { log.Printf("Close store error: %v", err) } } // envOr returns the environment variable name, or def when unset or empty. func envOr(name, def string) string { if v := os.Getenv(name); v != "" { return v } return def }