billing-service/internal/httpapi/handler.go
2026-04-12 15:42:09 +08:00

82 lines
2.0 KiB
Go

package httpapi
import (
"encoding/json"
"net/http"
"billing-service/internal/model"
"billing-service/internal/service"
)
type Handler struct {
service *service.Service
}
func New(svc *service.Service) *Handler {
return &Handler{service: svc}
}
func (h *Handler) Routes() http.Handler {
mux := http.NewServeMux()
mux.HandleFunc("/api/ping", h.ping)
mux.HandleFunc("/healthz", h.healthz)
mux.HandleFunc("/v1/status", h.status)
mux.HandleFunc("/v1/jobs/collect-and-rate", h.collectAndRate)
mux.HandleFunc("/v1/jobs/reconcile", h.reconcile)
return mux
}
func (h *Handler) ping(w http.ResponseWriter, r *http.Request) {
writeJSON(w, http.StatusOK, h.service.Ping())
}
func (h *Handler) healthz(w http.ResponseWriter, r *http.Request) {
ok, message := h.service.Health()
status := http.StatusOK
if !ok {
status = http.StatusServiceUnavailable
}
writeJSON(w, status, map[string]any{
"status": map[bool]string{true: "ok", false: "degraded"}[ok],
"message": message,
})
}
func (h *Handler) status(w http.ResponseWriter, r *http.Request) {
writeJSON(w, http.StatusOK, h.service.Status())
}
func (h *Handler) collectAndRate(w http.ResponseWriter, r *http.Request) {
if r.Method != http.MethodPost {
http.Error(w, "method not allowed", http.StatusMethodNotAllowed)
return
}
result, err := h.service.RunCollectAndRate(r.Context(), "collect-and-rate")
if err != nil {
writeJSON(w, http.StatusServiceUnavailable, result)
return
}
writeJSON(w, http.StatusOK, result)
}
func (h *Handler) reconcile(w http.ResponseWriter, r *http.Request) {
if r.Method != http.MethodPost {
http.Error(w, "method not allowed", http.StatusMethodNotAllowed)
return
}
result, err := h.service.RunCollectAndRate(r.Context(), "reconcile")
if err != nil {
writeJSON(w, http.StatusServiceUnavailable, result)
return
}
writeJSON(w, http.StatusOK, result)
}
func writeJSON(w http.ResponseWriter, status int, payload any) {
w.Header().Set("Content-Type", "application/json")
w.WriteHeader(status)
_ = json.NewEncoder(w).Encode(payload)
}
var _ = model.JobResult{}