package handler import ( "net/http" "github.com/gin-gonic/gin" "github.com/muyuqingfeng/iloom/shared/pkg/response" ws "github.com/muyuqingfeng/iloom/shared/pkg/websocket" "github.com/muyuqingfeng/iloom/textile-service/internal/service" ) type YarnHandler struct { svc *service.YarnService wsHub *ws.Hub } type CreateYarnStockRequest struct { Name string `json:"name" binding:"required"` Spec string `json:"spec"` Quantity float64 `json:"quantity"` Unit string `json:"unit"` MinStock float64 `json:"min_stock"` } type UpdateYarnStockRequest struct { Name string `json:"name"` Spec string `json:"spec"` Unit string `json:"unit"` MinStock float64 `json:"min_stock"` } type YarnRecordRequest struct { RecordType string `json:"record_type" binding:"required,oneof=in out"` Quantity float64 `json:"quantity" binding:"required,gt=0"` Unit string `json:"unit"` BatchNo string `json:"batch_no"` PlanID string `json:"plan_id"` Notes string `json:"notes"` } func NewYarnHandler(svc *service.YarnService, wsHub *ws.Hub) *YarnHandler { return &YarnHandler{svc: svc, wsHub: wsHub} } func (h *YarnHandler) List(c *gin.Context) { companyID := c.GetHeader("X-Company-ID") if companyID == "" { response.BadRequest(c, "missing X-Company-ID header") return } stocks, err := h.svc.List(c.Request.Context(), companyID) if err != nil { response.InternalError(c, err.Error()) return } response.OK(c, stocks) } func (h *YarnHandler) Create(c *gin.Context) { companyID := c.GetHeader("X-Company-ID") if companyID == "" { response.BadRequest(c, "missing X-Company-ID header") return } var req CreateYarnStockRequest if err := c.ShouldBindJSON(&req); err != nil { response.BadRequest(c, err.Error()) return } stock, err := h.svc.Create(c.Request.Context(), companyID, service.CreateYarnStockRequest{ Name: req.Name, Spec: req.Spec, Quantity: req.Quantity, Unit: req.Unit, MinStock: req.MinStock, }) if err != nil { response.InternalError(c, err.Error()) return } h.wsHub.BroadcastToCompany(companyID, &ws.Event{ Table: "yarn_stock", Action: "INSERT", }) c.JSON(http.StatusCreated, response.Response{ Code: 0, Message: "success", Data: stock, }) } func (h *YarnHandler) Update(c *gin.Context) { companyID := c.GetHeader("X-Company-ID") if companyID == "" { response.BadRequest(c, "missing X-Company-ID header") return } id := c.Param("id") var req UpdateYarnStockRequest if err := c.ShouldBindJSON(&req); err != nil { response.BadRequest(c, err.Error()) return } if err := h.svc.Update(c.Request.Context(), id, companyID, service.UpdateYarnStockRequest{ Name: req.Name, Spec: req.Spec, Unit: req.Unit, MinStock: req.MinStock, }); err != nil { response.InternalError(c, err.Error()) return } h.wsHub.BroadcastToCompany(companyID, &ws.Event{ Table: "yarn_stock", Action: "UPDATE", }) response.OK(c, gin.H{"message": "updated"}) } func (h *YarnHandler) AddRecord(c *gin.Context) { companyID := c.GetHeader("X-Company-ID") userID := c.GetHeader("X-User-ID") if companyID == "" || userID == "" { response.BadRequest(c, "missing required headers") return } yarnStockID := c.Param("id") var req YarnRecordRequest if err := c.ShouldBindJSON(&req); err != nil { response.BadRequest(c, err.Error()) return } if err := h.svc.AddRecord(c.Request.Context(), yarnStockID, companyID, userID, service.YarnRecordRequest{ RecordType: req.RecordType, Quantity: req.Quantity, Unit: req.Unit, BatchNo: req.BatchNo, PlanID: req.PlanID, Notes: req.Notes, }); err != nil { response.InternalError(c, err.Error()) return } h.wsHub.BroadcastToCompany(companyID, &ws.Event{ Table: "yarn_stock_records", Action: "INSERT", }) response.OK(c, gin.H{"message": "record added"}) }