package district import ( "cargo-erp-backend/internal/handlers/dto" districtimporter "cargo-erp-backend/internal/importers/district" "cargo-erp-backend/internal/usecases" "cargo-erp-backend/pkg/helpers" "cargo-erp-backend/pkg/importer" "cargo-erp-backend/pkg/response" "net/http" "github.com/gin-gonic/gin" ) type DistrictHandlerInterface interface { Router() } type DistrictHandler struct { Helper helpers.HelperInterface Group *gin.RouterGroup } func NewDistrictHandler(helper helpers.HelperInterface, g *gin.RouterGroup) DistrictHandlerInterface { return &DistrictHandler{Helper: helper, Group: g} } func (h *DistrictHandler) Router() { r := h.Group.Group("districts") { r.GET("/", h.GetAll) r.POST("/list", h.GetList) r.GET("/:id", h.GetByID) r.POST("/", h.Create) r.PUT("/:id", h.Update) r.DELETE("/:id", h.Delete) r.GET("/template", h.Template) r.POST("/import", h.Import) r.POST("/import/stop", h.ImportStop) r.GET("/import/status/:jobId", h.ImportStatus) } } func (h *DistrictHandler) GetAll(c *gin.Context) { userid, err := h.Helper.GetAuthInfo(c.GetString("auth")) if err != nil { response.Error(c, http.StatusUnauthorized, err.Error()) return } var req dto.DistrictFilterAllRequest if err := c.ShouldBindQuery(&req); err != nil { c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()}) return } u := usecases.NewDistrictUsecase(h.Helper, *userid) districts, _, err := u.GetAll(req) if err != nil { response.Error(c, http.StatusInternalServerError, err.Error()) return } var responseDTO = make([]dto.CreateDistrictResponse, 0) for _, v := range districts { var DTO dto.CreateDistrictResponse h.Helper.MapStructToStruct(v, "json", &DTO, "json") responseDTO = append(responseDTO, DTO) } response.Success(c, responseDTO) } func (h *DistrictHandler) GetList(c *gin.Context) { userid, err := h.Helper.GetAuthInfo(c.GetString("auth")) if err != nil { response.Error(c, http.StatusUnauthorized, err.Error()) return } var req dto.DataTableRequest if err := c.ShouldBindJSON(&req); err != nil { response.Error(c, http.StatusBadRequest, "Request Format request invalid") return } u := usecases.NewDistrictUsecase(h.Helper, *userid) res, err := u.GetList(req) if err != nil { response.Error(c, http.StatusInternalServerError, err.Error()) return } response.Success(c, res) return } func (h *DistrictHandler) GetByID(c *gin.Context) { userid, err := h.Helper.GetAuthInfo(c.GetString("auth")) if err != nil { response.Error(c, http.StatusUnauthorized, err.Error()) return } id := c.Param("id") u := usecases.NewDistrictUsecase(h.Helper, *userid) district, err := u.GetByID(id) if err != nil { response.Error(c, http.StatusNotFound, "district not found") return } response.Success(c, district) } func (h *DistrictHandler) Create(c *gin.Context) { var req dto.CreateDistrictRequest if err := c.BindJSON(&req); err != nil { response.Error(c, http.StatusBadRequest, err.Error()) return } userid, err := h.Helper.GetAuthInfo(c.GetString("auth")) if err != nil { response.Error(c, http.StatusUnauthorized, err.Error()) return } var merchantid *string = nil if userid.UsersRole_Relation.RoleKey != "SPM" { merchantid = userid.MerchantID } createdBy := userid.ID u := usecases.NewDistrictUsecase(h.Helper, *userid) district, err := u.Create(req.Name, req.ProvinceID, req.CityID, createdBy, merchantid) if err != nil { response.Error(c, http.StatusInternalServerError, err.Error()) return } var responseDTO dto.CreateDistrictResponse h.Helper.MapStructToStruct(district, "json", &responseDTO, "json") response.Created(c, responseDTO) } func (h *DistrictHandler) Update(c *gin.Context) { id := c.Param("id") var req dto.UpdateDistrictRequest if err := c.BindJSON(&req); err != nil { response.Error(c, http.StatusBadRequest, err.Error()) return } userid, err := h.Helper.GetAuthInfo(c.GetString("auth")) if err != nil { response.Error(c, http.StatusUnauthorized, err.Error()) return } updatedBy := userid.ID u := usecases.NewDistrictUsecase(h.Helper, *userid) district, err := u.Update(id, req.Name, req.ProvinceID, req.CityID, updatedBy) if err != nil { response.Error(c, http.StatusInternalServerError, err.Error()) return } var responseDTO dto.CreateDistrictResponse h.Helper.MapStructToStruct(district, "json", &responseDTO, "json") response.Success(c, responseDTO) } func (h *DistrictHandler) Delete(c *gin.Context) { userid, err := h.Helper.GetAuthInfo(c.GetString("auth")) if err != nil { response.Error(c, http.StatusUnauthorized, err.Error()) return } id := c.Param("id") u := usecases.NewDistrictUsecase(h.Helper, *userid) if err := u.Delete(id); err != nil { response.Error(c, http.StatusInternalServerError, err.Error()) return } response.Success(c, map[string]interface{}{"message": "district deleted"}) } func (h *DistrictHandler) Template(c *gin.Context) { userid, err := h.Helper.GetAuthInfo(c.GetString("auth")) if err != nil { response.Error(c, http.StatusUnauthorized, err.Error()) return } handler := districtimporter.NewDistrictImportHandler(*userid, h.Helper) imp := importer.NewImporter(h.Helper, handler) imp.ServeTemplate(c.Writer) } func (h *DistrictHandler) Import(c *gin.Context) { userid, err := h.Helper.GetAuthInfo(c.GetString("auth")) if err != nil { response.Error(c, http.StatusUnauthorized, err.Error()) return } file, header, err := c.Request.FormFile("file") if err != nil { response.Error(c, http.StatusBadRequest, "File is required") return } defer file.Close() handler := districtimporter.NewDistrictImportHandler(*userid, h.Helper) imp := importer.NewImporter(h.Helper, handler) result, err := imp.Process(file, userid.ID, header.Filename) if err != nil { response.Error(c, http.StatusBadRequest, err.Error()) return } var importLogs []dto.ImportLog for _, l := range result.Logs { importLogs = append(importLogs, dto.ImportLog{ Row: l.Row, Status: l.Status, Data: l.Data, Message: l.Message, }) } response.Success(c, dto.ImportDistrictResponse{ JobID: result.JobID, TotalRows: result.TotalRows, Imported: result.Imported, Skipped: result.Skipped, Logs: importLogs, Errors: result.Errors, IsAsync: result.IsAsync, Message: result.Message, }) } func (h *DistrictHandler) ImportStatus(c *gin.Context) { userid, err := h.Helper.GetAuthInfo(c.GetString("auth")) if err != nil { response.Error(c, http.StatusUnauthorized, err.Error()) return } jobId := c.Param("jobId") handler := districtimporter.NewDistrictImportHandler(*userid, h.Helper) imp := importer.NewImporter(h.Helper, handler) job, logs, err := imp.GetJobStatus(jobId) if err != nil { response.Error(c, http.StatusNotFound, "Job not found") return } response.Success(c, map[string]interface{}{ "job": job, "logs": logs, }) } func (h *DistrictHandler) ImportStop(c *gin.Context) { userid, err := h.Helper.GetAuthInfo(c.GetString("auth")) if err != nil { response.Error(c, http.StatusUnauthorized, err.Error()) return } var req dto.StopImportRequest if err := c.BindJSON(&req); err != nil { response.Error(c, http.StatusBadRequest, "job_id is required") return } handler := districtimporter.NewDistrictImportHandler(*userid, h.Helper) imp := importer.NewImporter(h.Helper, handler) if err := imp.StopJob(req.JobID); err != nil { response.Error(c, http.StatusBadRequest, err.Error()) return } response.Success(c, map[string]interface{}{"message": "Job stopped"}) }