package admin import ( "bindbox-game/internal/code" "bindbox-game/internal/pkg/core" "bindbox-game/internal/pkg/validation" "bindbox-game/internal/service/douyin" "fmt" "net/http" "strconv" ) // ---------- 抖店配置 API ---------- type getDouyinConfigResponse struct { Cookie string `json:"cookie"` IntervalMinutes int `json:"interval_minutes"` } func (h *handler) GetDouyinConfig() core.HandlerFunc { return func(ctx core.Context) { cfg, err := h.douyinSvc.GetConfig(ctx.RequestContext()) if err != nil { ctx.AbortWithError(core.Error(http.StatusBadRequest, code.ServerError, validation.Error(err))) return } ctx.Payload(getDouyinConfigResponse{ Cookie: cfg.Cookie, IntervalMinutes: cfg.IntervalMinutes, }) } } type saveDouyinConfigRequest struct { Cookie string `json:"cookie"` IntervalMinutes int `json:"interval_minutes"` } func (h *handler) SaveDouyinConfig() core.HandlerFunc { return func(ctx core.Context) { req := new(saveDouyinConfigRequest) if err := ctx.ShouldBindJSON(req); err != nil { ctx.AbortWithError(core.Error(http.StatusBadRequest, code.ParamBindError, validation.Error(err))) return } if err := h.douyinSvc.SaveConfig(ctx.RequestContext(), req.Cookie, req.IntervalMinutes); err != nil { ctx.AbortWithError(core.Error(http.StatusBadRequest, code.ServerError, validation.Error(err))) return } ctx.Payload(pcSimpleMessage{Message: "保存成功"}) } } // ---------- 抖店订单列表 API ---------- type listDouyinOrdersRequest struct { Page int `form:"page"` PageSize int `form:"page_size"` Status *int `form:"status"` } type douyinOrderItem struct { ID int64 `json:"id"` ShopOrderID string `json:"shop_order_id"` OrderStatus int32 `json:"order_status"` OrderStatusText string `json:"order_status_text"` DouyinUserID string `json:"douyin_user_id"` LocalUserID int64 `json:"local_user_id"` LocalUserNickname string `json:"local_user_nickname"` ActualReceiveAmount string `json:"actual_receive_amount"` PayTypeDesc string `json:"pay_type_desc"` Remark string `json:"remark"` UserNickname string `json:"user_nickname"` CreatedAt string `json:"created_at"` } type listDouyinOrdersResponse struct { Page int `json:"page"` PageSize int `json:"page_size"` Total int64 `json:"total"` List []douyinOrderItem `json:"list"` } func (h *handler) ListDouyinOrders() core.HandlerFunc { return func(ctx core.Context) { req := new(listDouyinOrdersRequest) if err := ctx.ShouldBindForm(req); err != nil { ctx.AbortWithError(core.Error(http.StatusBadRequest, code.ParamBindError, validation.Error(err))) return } orders, total, err := h.douyinSvc.ListOrders(ctx.RequestContext(), req.Page, req.PageSize, req.Status) if err != nil { ctx.AbortWithError(core.Error(http.StatusBadRequest, code.ServerError, validation.Error(err))) return } // 获取匹配用户的昵称 userNicknameMap := make(map[int64]string) var userIDs []int64 for _, o := range orders { if uid, err := strconv.ParseInt(o.LocalUserID, 10, 64); err == nil && uid > 0 { userIDs = append(userIDs, uid) } } if len(userIDs) > 0 { var users []struct { ID int64 Nickname string } h.repo.GetDbR().Table("users").Where("id IN ?", userIDs).Select("id, nickname").Find(&users) for _, u := range users { userNicknameMap[u.ID] = u.Nickname } } // 构建响应 list := make([]douyinOrderItem, len(orders)) for i, o := range orders { uid, _ := strconv.ParseInt(o.LocalUserID, 10, 64) list[i] = douyinOrderItem{ ID: o.ID, ShopOrderID: o.ShopOrderID, OrderStatus: o.OrderStatus, OrderStatusText: getOrderStatusText(o.OrderStatus), DouyinUserID: o.DouyinUserID, LocalUserID: uid, LocalUserNickname: userNicknameMap[uid], ActualReceiveAmount: formatAmount(o.ActualReceiveAmount), PayTypeDesc: o.PayTypeDesc, Remark: o.Remark, UserNickname: o.UserNickname, CreatedAt: o.CreatedAt.Format("2006-01-02 15:04:05"), } } ctx.Payload(listDouyinOrdersResponse{ Page: req.Page, PageSize: req.PageSize, Total: total, List: list, }) } } // ---------- 手动同步 API ---------- type syncDouyinOrdersResponse struct { Message string `json:"message"` TotalFetched int `json:"total_fetched"` NewOrders int `json:"new_orders"` MatchedUsers int `json:"matched_users"` } func (h *handler) SyncDouyinOrders() core.HandlerFunc { return func(ctx core.Context) { result, err := h.douyinSvc.FetchAndSyncOrders(ctx.RequestContext()) if err != nil { ctx.AbortWithError(core.Error(http.StatusBadRequest, code.ServerError, validation.Error(err))) return } ctx.Payload(syncDouyinOrdersResponse{ Message: "同步成功", TotalFetched: result.TotalFetched, NewOrders: result.NewOrders, MatchedUsers: result.MatchedUsers, }) } } // ---------- 辅助函数 ---------- func getOrderStatusText(status int32) string { switch status { case 1: return "待付款" case 2: return "待发货" case 3: return "已发货" case 4: return "已取消" case 5: return "已完成" default: return "未知" } } func formatAmount(amountCents int64) string { yuan := float64(amountCents) / 100.0 return fmt.Sprintf("%.2f", yuan) } // SetDouyinService 设置抖店服务 (用于 handler 初始化) func (h *handler) SetDouyinService(svc douyin.Service) { h.douyinSvc = svc }