Files
satusehat-service/cmd/satusehat/main.go
T
2026-04-14 01:23:34 +00:00

142 lines
4.8 KiB
Go

package main
import (
"context"
"net/http"
"os"
"os/signal"
"syscall"
"service/internal/infrastructure/cache"
"service/internal/infrastructure/config"
"service/internal/infrastructure/database"
httpServer "service/internal/infrastructure/transport/http/servers"
satuSehatFactory "service/internal/interfaces/satusehat"
"service/pkg/logger"
satuSehatAuth "service/internal/satusehat/reference/auth"
satuSehatKfa "service/internal/satusehat/reference/kfa"
satuSehatLocation "service/internal/satusehat/reference/location"
satuSehatOrganization "service/internal/satusehat/reference/organization"
satuSehatPatient "service/internal/satusehat/reference/patient"
satuSehatPractitioner "service/internal/satusehat/reference/practitioner"
satuSehatCondition "service/internal/satusehat/usecase/condition"
satuSehatEncounter "service/internal/satusehat/usecase/encounter"
satuSehatProcedure "service/internal/satusehat/usecase/procedure"
_ "service/docs/swagger" // Import swagger docs
"golang.org/x/sync/errgroup"
)
func main() {
// 1. Load Config
cfg := config.LoadConfig()
// 2. Init Logger khusus untuk service Satu Sehat
loggerConfig := logger.Config{
Level: cfg.Logger.Level,
Format: cfg.Logger.Format,
Output: "both",
ServiceName: "service-satusehat", // Penanda log
EnableCaller: cfg.Server.Mode != "production",
Environment: cfg.Server.Mode,
}
logger.Init(loggerConfig)
logger.Default().Info("SatuSehat Microservice starting...",
logger.String("environment", cfg.Server.Mode),
logger.String("log_level", cfg.Logger.Level),
)
if err := cfg.Validate(); err != nil {
logger.Default().Fatal("Config validation failed", logger.ErrorField(err))
}
// 3. Init Database Manager
dbService := database.New(cfg)
defer dbService.Close()
gormDB, err := dbService.GetGormDB("default")
if err != nil {
logger.Default().Fatal("Failed to get primary database", logger.ErrorField(err))
}
// 4. Init Cache
cacheFactory := cache.NewFactory(cfg.Cache)
cacheManager, err := cacheFactory.CreateManager()
if err != nil {
logger.Default().Fatal("Failed to initialize cache manager", logger.ErrorField(err))
}
defer cacheManager.Close()
// 5. Init Layers (Hanya Modul Satu Sehat)
satusehatFact := satuSehatFactory.NewSatuSehatFactory(cfg.SatuSehat)
satusehatClient := satusehatFact.Client()
// - Reference Services
satuSehatAuthSvc := satuSehatAuth.NewService(satusehatClient, cacheManager)
satuSehatPatientSvc := satuSehatPatient.NewService(satuSehatPatient.NewRepository(satusehatClient))
satuSehatPractitionerSvc := satuSehatPractitioner.NewService(satuSehatPractitioner.NewRepository(satusehatClient))
satuSehatOrganizationSvc := satuSehatOrganization.NewService(satuSehatOrganization.NewRepository(satusehatClient))
satuSehatLocationSvc := satuSehatLocation.NewService(satuSehatLocation.NewRepository(satusehatClient))
satuSehatKfaSvc := satuSehatKfa.NewService(satuSehatKfa.NewRepository(satusehatClient))
// - Usecase Services
satuSehatEncounterSvc := satuSehatEncounter.NewService(satuSehatEncounter.NewRepository(satusehatClient, dbService))
satuSehatProcedureSvc := satuSehatProcedure.NewService(satuSehatProcedure.NewRepository(satusehatClient))
satuSehatConditionSvc := satuSehatCondition.NewService(satuSehatCondition.NewRepository(satusehatClient))
// 6. Server Orchestration
ctx, cancel := context.WithCancel(context.Background())
defer cancel()
g, ctx := errgroup.WithContext(ctx)
// --- Start REST Server (Hanya me-load endpoint Satu Sehat & Health) ---
if cfg.Server.REST.Enabled {
registry := &httpServer.ServiceRegistry{
Config: cfg,
DBManager: dbService,
PrimaryDB: gormDB,
CacheManager: cacheManager,
SatuSehat: &httpServer.SatuSehatServices{
Auth: satuSehatAuthSvc,
Patient: satuSehatPatientSvc,
Practitioner: satuSehatPractitionerSvc,
Organization: satuSehatOrganizationSvc,
Location: satuSehatLocationSvc,
KFA: satuSehatKfaSvc,
Encounter: satuSehatEncounterSvc,
Procedure: satuSehatProcedureSvc,
Condition: satuSehatConditionSvc,
},
}
restSrv := httpServer.NewHTTPServer(&cfg.Server.REST, registry)
g.Go(func() error {
logger.Default().Info("SatuSehat REST API running", logger.Int("port", cfg.Server.REST.Port))
if err := restSrv.Start(&cfg.Server); err != nil && err != http.ErrServerClosed {
return err
}
return nil
})
}
// --- Graceful Shutdown Listener ---
g.Go(func() error {
quit := make(chan os.Signal, 1)
signal.Notify(quit, syscall.SIGINT, syscall.SIGTERM)
<-quit
logger.Default().Warn("Signal received, shutting down SatuSehat service...")
cancel()
return nil
})
if err := g.Wait(); err != nil {
logger.Default().Error("SatuSehat service shutdown with error", logger.ErrorField(err))
} else {
logger.Default().Info("SatuSehat service shutdown successful")
}
}