AllAi/backend/go/cmd/server/main.go
2025-11-14 21:54:04 +03:00

73 lines
1.7 KiB
Go

package main
import (
"context"
"fmt"
"log"
"net/http"
"os"
"os/signal"
"syscall"
"time"
"github.com/allai/allai-backend/internal/app"
"github.com/allai/allai-backend/internal/config"
"github.com/allai/allai-backend/internal/httpapi"
"github.com/allai/allai-backend/internal/provider/mock"
)
func main() {
cfg := config.Load()
logger := log.New(os.Stdout, "[allai-backend] ", log.LstdFlags|log.Lmsgprefix)
var provider app.GenerationProvider
switch cfg.ProviderKind {
case "mock":
provider = mock.New()
default:
logger.Printf("provider %q not recognised, falling back to mock provider", cfg.ProviderKind)
provider = mock.New()
}
service := app.NewService(provider)
router := httpapi.NewRouter(service, logger)
server := &http.Server{
Addr: cfg.Address(),
Handler: router,
ReadTimeout: 15 * time.Second,
WriteTimeout: 60 * time.Second,
IdleTimeout: 90 * time.Second,
}
go func() {
logger.Printf("server starting on %s", cfg.Address())
if err := server.ListenAndServe(); err != nil && err != http.ErrServerClosed {
logger.Fatalf("http server failed: %v", err)
}
}()
shutdown(server, logger)
}
func shutdown(server *http.Server, logger *log.Logger) {
ctx, stop := signal.NotifyContext(context.Background(), syscall.SIGINT, syscall.SIGTERM)
defer stop()
<-ctx.Done()
logger.Println("shutdown signal received, draining requests…")
shutdownCtx, cancel := context.WithTimeout(context.Background(), 20*time.Second)
defer cancel()
if err := server.Shutdown(shutdownCtx); err != nil {
logger.Printf("graceful shutdown failed: %v", err)
if closeErr := server.Close(); closeErr != nil {
logger.Printf("forced close failed: %v", closeErr)
}
}
logger.Println("server stopped cleanly")
}