package handlers import ( "net/http" "strconv" "github.com/calendarapi/internal/middleware" "github.com/calendarapi/internal/models" "github.com/calendarapi/internal/service" "github.com/calendarapi/internal/utils" "github.com/go-chi/chi/v5" ) type ContactHandler struct { contactSvc *service.ContactService } func NewContactHandler(contactSvc *service.ContactService) *ContactHandler { return &ContactHandler{contactSvc: contactSvc} } func (h *ContactHandler) List(w http.ResponseWriter, r *http.Request) { userID, _ := middleware.GetUserID(r.Context()) q := r.URL.Query() var search *string if s := q.Get("search"); s != "" { search = &s } limit := 50 if l := q.Get("limit"); l != "" { if v, err := strconv.Atoi(l); err == nil { limit = v } } contacts, cursor, err := h.contactSvc.List(r.Context(), userID, search, limit, q.Get("cursor")) if err != nil { utils.WriteError(w, err) return } utils.WriteList(w, contacts, models.PageInfo{Limit: int(utils.ClampLimit(limit)), NextCursor: cursor}) } func (h *ContactHandler) Create(w http.ResponseWriter, r *http.Request) { userID, _ := middleware.GetUserID(r.Context()) var req struct { FirstName *string `json:"first_name"` LastName *string `json:"last_name"` Email *string `json:"email"` Phone *string `json:"phone"` Company *string `json:"company"` Notes *string `json:"notes"` } if err := utils.DecodeJSON(r, &req); err != nil { utils.WriteError(w, err) return } contact, err := h.contactSvc.Create(r.Context(), userID, service.CreateContactRequest{ FirstName: req.FirstName, LastName: req.LastName, Email: req.Email, Phone: req.Phone, Company: req.Company, Notes: req.Notes, }) if err != nil { utils.WriteError(w, err) return } utils.WriteJSON(w, http.StatusOK, map[string]interface{}{"contact": contact}) } func (h *ContactHandler) Get(w http.ResponseWriter, r *http.Request) { userID, _ := middleware.GetUserID(r.Context()) contactID, err := utils.ValidateUUID(chi.URLParam(r, "id")) if err != nil { utils.WriteError(w, err) return } contact, err := h.contactSvc.Get(r.Context(), userID, contactID) if err != nil { utils.WriteError(w, err) return } utils.WriteJSON(w, http.StatusOK, map[string]interface{}{"contact": contact}) } func (h *ContactHandler) Update(w http.ResponseWriter, r *http.Request) { userID, _ := middleware.GetUserID(r.Context()) contactID, err := utils.ValidateUUID(chi.URLParam(r, "id")) if err != nil { utils.WriteError(w, err) return } var req struct { FirstName *string `json:"first_name"` LastName *string `json:"last_name"` Email *string `json:"email"` Phone *string `json:"phone"` Company *string `json:"company"` Notes *string `json:"notes"` } if err := utils.DecodeJSON(r, &req); err != nil { utils.WriteError(w, err) return } contact, err := h.contactSvc.Update(r.Context(), userID, contactID, service.UpdateContactRequest{ FirstName: req.FirstName, LastName: req.LastName, Email: req.Email, Phone: req.Phone, Company: req.Company, Notes: req.Notes, }) if err != nil { utils.WriteError(w, err) return } utils.WriteJSON(w, http.StatusOK, map[string]interface{}{"contact": contact}) } func (h *ContactHandler) Delete(w http.ResponseWriter, r *http.Request) { userID, _ := middleware.GetUserID(r.Context()) contactID, err := utils.ValidateUUID(chi.URLParam(r, "id")) if err != nil { utils.WriteError(w, err) return } if err := h.contactSvc.Delete(r.Context(), userID, contactID); err != nil { utils.WriteError(w, err) return } utils.WriteOK(w) }