package server import ( "encoding/json" "log/slog" "net/http" "git.g3e.fr/H6N/account/internal/auth" "git.g3e.fr/H6N/account/internal/config" "git.g3e.fr/H6N/account/internal/handler" "git.g3e.fr/H6N/account/internal/pipeline" "git.g3e.fr/H6N/account/internal/snapshot" "git.g3e.fr/H6N/account/internal/store" "github.com/jackc/pgx/v5/pgxpool" ) type Server struct { mux *http.ServeMux pool *pgxpool.Pool logger *slog.Logger cfg *config.Config } func New(cfg *config.Config, pool *pgxpool.Pool, logger *slog.Logger) *Server { s := &Server{ mux: http.NewServeMux(), pool: pool, logger: logger, cfg: cfg, } s.routes() return s } func (s *Server) ServeHTTP(w http.ResponseWriter, r *http.Request) { // /health est exempt d'auth. Toutes les autres routes passent par le middleware owner. if r.URL.Path == "/health" { s.mux.ServeHTTP(w, r) return } auth.Middleware(s.mux).ServeHTTP(w, r) } func (s *Server) routes() { st := store.New(s.pool) horizonDays := 30 var pipelineCfg pipeline.Config if s.cfg != nil { horizonDays = s.cfg.SnapshotHorizonDays pipelineCfg = pipeline.Config{ OpenFIGIKey: s.cfg.OpenFIGIKey, CoinGeckoKey: s.cfg.CoinGeckoKey, } } pl := pipeline.New(st, pipelineCfg, s.logger) eng := snapshot.New(st, s.logger, horizonDays).WithBackfiller(pl) handler.NewInstrumentHandler(st).RegisterRoutes(s.mux) handler.NewAccountHandler(st).RegisterRoutes(s.mux) handler.NewTransactionHandler(st).RegisterRoutes(s.mux) handler.NewSnapshotHandler(eng).RegisterRoutes(s.mux) s.mux.HandleFunc("GET /health", s.handleHealth) } func (s *Server) handleHealth(w http.ResponseWriter, r *http.Request) { if err := s.pool.Ping(r.Context()); err != nil { s.logger.Error("health check failed", "error", err) http.Error(w, "database unavailable", http.StatusServiceUnavailable) return } w.Header().Set("Content-Type", "application/json") json.NewEncoder(w).Encode(map[string]string{"status": "ok"}) }