package codigos import ( "net/http" "github.com/gin-gonic/gin" "github.com/google/uuid" ) type Handler struct { service *Service } func NewHandler(service *Service) *Handler { return &Handler{service: service} } // Create godoc // @Summary Create Access Code // @Tags codigos // @Accept json // @Produce json // @Param req body CreateCodigoInput true "Req" // @Success 201 {object} map[string]interface{} // @Router /api/codigos-acesso [post] func (h *Handler) Create(c *gin.Context) { var req CreateCodigoInput if err := c.ShouldBindJSON(&req); err != nil { c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()}) return } // Extract region from header regiao := c.GetString("regiao") if regiao == "" { regiao = c.GetHeader("x-regiao") } req.Regiao = regiao code, err := h.service.Create(c.Request.Context(), req) if err != nil { c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()}) return } c.JSON(http.StatusCreated, gin.H{"id": uuid.UUID(code.ID.Bytes).String(), "codigo": code.Codigo}) } // List godoc // @Summary List Access Codes // @Tags codigos // @Produce json // @Success 200 {array} map[string]interface{} // @Router /api/codigos-acesso [get] func (h *Handler) List(c *gin.Context) { regiao := c.GetString("regiao") if regiao == "" { regiao = c.GetHeader("x-regiao") } codes, err := h.service.List(c.Request.Context(), regiao) if err != nil { c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()}) return } resp := make([]map[string]interface{}, len(codes)) for i, v := range codes { var empID, empNome string if v.EmpresaID.Valid { empID = uuid.UUID(v.EmpresaID.Bytes).String() } if v.EmpresaNome.Valid { empNome = v.EmpresaNome.String } resp[i] = map[string]interface{}{ "id": uuid.UUID(v.ID.Bytes).String(), "codigo": v.Codigo, "descricao": v.Descricao.String, "validade_dias": v.ValidadeDias, "criado_em": v.CriadoEm.Time, "expira_em": v.ExpiraEm.Time, "ativo": v.Ativo, "usos": v.Usos, "empresa_id": empID, "empresa_nome": empNome, } } c.JSON(http.StatusOK, resp) } // Delete godoc // @Summary Delete Access Code // @Tags codigos // @Param id path string true "ID" // @Success 200 {object} map[string]string // @Router /api/codigos-acesso/{id} [delete] func (h *Handler) Delete(c *gin.Context) { id := c.Param("id") if id == "" { c.JSON(http.StatusBadRequest, gin.H{"error": "id required"}) return } err := h.service.Delete(c.Request.Context(), id) if err != nil { c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()}) return } c.JSON(http.StatusOK, gin.H{"message": "deleted"}) } // Verify godoc // @Summary Verify Access Code // @Tags codigos // @Param code query string true "Code" // @Success 200 {object} map[string]bool // @Failure 400 {object} map[string]string // @Router /api/public/codigos-acesso/verificar [get] func (h *Handler) Verify(c *gin.Context) { code := c.Query("code") if code == "" { c.JSON(http.StatusBadRequest, gin.H{"error": "code required"}) return } codeData, err := h.service.Verify(c.Request.Context(), code) if err != nil { // Distinguish validation error from DB error strictly? // For security, just say invalid. // But service returns specific AppError. if _, ok := err.(*AppError); ok { c.JSON(http.StatusBadRequest, gin.H{"valid": false, "error": err.Error()}) return } // If check failed (not found etc), return 404 or 400 c.JSON(http.StatusBadRequest, gin.H{"valid": false, "error": "Código inválido"}) return } // Prepare response resp := gin.H{"valid": true} if codeData.EmpresaID.Valid { resp["empresa_id"] = uuid.UUID(codeData.EmpresaID.Bytes).String() } if codeData.EmpresaNome.Valid { resp["empresa_nome"] = codeData.EmpresaNome.String } c.JSON(http.StatusOK, resp) }