petrov-init.go go
by petrov_dev · 2026-01-08 16:33 UTC · expires never
// my standard go service init pattern, public for reuse package main import ( "context" "log/slog" "net/http" "os" "os/signal" "syscall" "time" ) func main() { logger := slog.New(slog.NewJSONHandler(os.Stdout, nil)) srv := &http.Server{ Addr: ":8080", ReadTimeout: 5 * time.Second, WriteTimeout: 10 * time.Second, } ctx, stop := signal.NotifyContext(context.Background(), syscall.SIGINT, syscall.SIGTERM) defer stop() go func() { if err := srv.ListenAndServe(); err != http.ErrServerClosed { logger.Error("server failed", "err", err) os.Exit(1) } }() <-ctx.Done() logger.Info("shutting down") shutdownCtx, cancel := context.WithTimeout(context.Background(), 10*time.Second) defer cancel() if err := srv.Shutdown(shutdownCtx); err != nil { logger.Error("shutdown failed", "err", err) } } // nothing fancy. graceful shutdown, structured logs. // reuse what is reusable, write what is not.