Aditya Siregar bc64eb20ea add dukcapil
2026-05-07 04:01:32 +07:00

100 lines
2.0 KiB
Go

package app
import (
"context"
"log"
"net/http"
"os"
"os/signal"
"syscall"
"time"
"go-backend-template/config"
"go-backend-template/internal/client"
"go-backend-template/internal/handler"
"go-backend-template/internal/router"
"go-backend-template/internal/service"
)
type App struct {
server *http.Server
router *router.Router
shutdown chan os.Signal
}
func NewApp() *App {
return &App{
shutdown: make(chan os.Signal, 1),
}
}
func (a *App) Initialize(cfg *config.Config) error {
healthHandler := handler.NewHealthHandler()
dukcapilClient := client.NewDukcapilClient(cfg.Dukcapil)
dukcapilService := service.NewDukcapilService(dukcapilClient)
dukcapilHandler := handler.NewDukcapilHandler(dukcapilService)
a.router = router.NewRouter(
cfg,
nil, // authHandler
nil, // authMiddleware
healthHandler,
nil, // userHandler
dukcapilHandler,
)
return nil
}
func (a *App) Start(port string) error {
engine := a.router.Init()
// Debug: log what port value we received
log.Printf("DEBUG: Received port value: %q", port)
// Ensure proper address format
// Only accept port number, not full addresses
addr := ":" + port
if port == "" {
addr = ":8080" // default port
}
log.Printf("DEBUG: Final address: %q", addr)
a.server = &http.Server{
Addr: addr,
Handler: engine,
ReadTimeout: 15 * time.Second,
WriteTimeout: 15 * time.Second,
IdleTimeout: 60 * time.Second,
}
signal.Notify(a.shutdown, os.Interrupt, syscall.SIGTERM)
go func() {
log.Printf("Server starting on port %s", port)
if err := a.server.ListenAndServe(); err != nil && err != http.ErrServerClosed {
log.Fatalf("Failed to start server: %v", err)
}
}()
<-a.shutdown
log.Println("Shutting down server...")
ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second)
defer cancel()
if err := a.server.Shutdown(ctx); err != nil {
log.Printf("Server forced to shutdown: %v", err)
return err
}
log.Println("Server exited gracefully")
return nil
}
func (a *App) Shutdown() {
close(a.shutdown)
}