diff --git a/business/jxcallback/scheduler/basesch/basesch.go b/business/jxcallback/scheduler/basesch/basesch.go index 5e441c46e..cc29ffddb 100644 --- a/business/jxcallback/scheduler/basesch/basesch.go +++ b/business/jxcallback/scheduler/basesch/basesch.go @@ -135,13 +135,16 @@ func (c *BaseScheduler) SelfDeliverDelivering(order *model.GoodsOrder, userName orderStatus, _ := partner.GetPurchasePlatformFromVendorID(order.VendorID).OrderLogisticsStatus(utils.Str2Int64(order.VendorOrderID)) if orderStatus == 100 { // 美团取消配送单 partner.CurOrderManager.OnOrderMsg(order, "美团外卖转自送成功.", "") + return nil } else if strings.Contains(err.Error(), "包裹不存在") || strings.Contains(err.Error(), "运单不存在") || strings.Contains(err.Error(), "1071") || strings.Contains(err.Error(), "1014") || strings.Contains(err.Error(), "invalid character 'o' looking for beginning of value") { partner.CurOrderManager.OnOrderMsg(order, "美团外卖转自送可能成功,异常:", err.Error()) err = nil + return nil } else { bill, _ := partner.CurOrderManager.LoadWaybill(order.VendorWaybillID, order.WaybillVendorID) - c.CancelWaybill(bill, partner.CancelWaybillReasonOther, partner.CancelWaybillReasonStrActive) + err = c.CancelWaybill(bill, partner.CancelWaybillReasonOther, partner.CancelWaybillReasonStrActive) partner.CurOrderManager.OnOrderMsg(order, "美团外卖运单无法取消,", err.Error()) + return err } } diff --git a/business/jxstore/common/common.go b/business/jxstore/common/common.go index 15d24b520..8a8110240 100644 --- a/business/jxstore/common/common.go +++ b/business/jxstore/common/common.go @@ -283,7 +283,14 @@ func AddVendorOrgCode(ctx *jxcontext.Context, vendorOrgCode *model.VendorOrgCode if len(list) > 0 { return fmt.Errorf("库里有这个账号了,[%v]", vendorOrgCode.VendorOrgCode) } - dao.WrapAddIDCULDEntity(vendorOrgCode, ctx.GetUserName()) + + var userName string + if ctx != nil { + userName = ctx.GetUserName() + } else { + userName = "system" + } + dao.WrapAddIDCULDEntity(vendorOrgCode, userName) dao.CreateEntity(db, vendorOrgCode) return err } diff --git a/business/model/api_config.go b/business/model/api_config.go index 673251492..6af4aee42 100644 --- a/business/model/api_config.go +++ b/business/model/api_config.go @@ -14,15 +14,15 @@ const ( VendorIDMTWM = 1 VendorIDELM = 2 VendorIDEBAI = 3 + VendorIDYB = 4 //银豹 + VendorIDJDShop = 5 //京东商城 + VendorIDJX = 9 // 这是一个假的京西VendorID VendorIDGD = 10 - VendorIDYB = 4 //银豹 - VendorIDJDShop = 5 //京东商城 VendorIDWSC = 11 // 微盟微商城 - VendorIDPurchaseEnd = 11 - VendorIDJX = 9 // 这是一个假的京西VendorID VendorGoMei = 12 // 国美 VendorIDTT = 13 // 抖音平台小程序 VendorIDDD = 14 // 抖店 + VendorIDPurchaseEnd = 15 VendorIDWXPay = 51 // 微信支付 @@ -86,6 +86,7 @@ var ( VendorNames = map[int]string{ VendorIDJD: "Jd", VendorIDMTWM: "Mtwm", + VendorIDDD: "Dd", // 抖店 VendorIDELM: "Elm", VendorIDEBAI: "Ebai", VendorIDWSC: "Wsc", diff --git a/business/model/dao/dao_user.go b/business/model/dao/dao_user.go index 3fe4f28ba..086676d90 100644 --- a/business/model/dao/dao_user.go +++ b/business/model/dao/dao_user.go @@ -32,7 +32,7 @@ func GetUserByID(db *DaoDB, fieldName, fieldValue string) (user *model.User, err sql := fmt.Sprintf(` SELECT * FROM user t1 - WHERE t1.deleted_at = ? AND t1.status = ? AND t1.%s = ? + WHERE t1.deleted_at = ? AND t1.status = ? AND t1.%s = ? `, fieldName) sqlParams := []interface{}{ utils.DefaultTimeValue, diff --git a/business/model/store.go b/business/model/store.go index d74c7eaa0..abb290bfb 100644 --- a/business/model/store.go +++ b/business/model/store.go @@ -301,7 +301,6 @@ var ( type Store struct { ModelIDCULD - OriginalName string `orm:"-" json:"originalName"` Name string `orm:"size(255)" json:"name"` CityCode int `orm:"default(0);null" json:"cityCode"` // todo ? @@ -995,3 +994,18 @@ func (*BrandCategoryMap) TableUnique() [][]string { []string{"BrandID", "CategoryID", "DeletedAt"}, } } + +// 抖店 创建运费模板映射关系 +type FreightTemplate struct { + ModelIDCULD + StoreID int64 `orm:"column(store_id)" json:"storeID"` //京西本地门店ID + VendorStoreID int64 `orm:"column(vendor_store_id)" json:"vendorStoreID"` //抖店平台门店ID + TemplateID int64 `orm:"column(template_id)" json:"templateID"` //运费模板ID + TemplateDetail string `orm:"column(template_detail)" json:"templateDetail"` //json转化的模板信息 +} + +func (*FreightTemplate) TableUnique() [][]string { + return [][]string{ + []string{"StoreID", "TemplateID", "VendorStoreID"}, + } +} diff --git a/business/partner/delivery/dada/waybill.go b/business/partner/delivery/dada/waybill.go index 9e178fa54..bd571ad1a 100644 --- a/business/partner/delivery/dada/waybill.go +++ b/business/partner/delivery/dada/waybill.go @@ -116,6 +116,12 @@ func (c *DeliveryHandler) callbackMsg2Waybill(msg *dadaapi.CallbackMsg) (retVal } retVal.StatusTime = utils.Timestamp2Time(updateTime) retVal.VendorOrderID, retVal.OrderVendorID = jxutils.SplitUniversalOrderID(msg.OrderID) + + var good *model.GoodsOrder + sql := `SELECT * FROM goods_order WHERE vendor_order_id = ? ORDER BY order_created_at DESC LIMIT 1 OFFSET 0` + sqlParams := []interface{}{msg.OrderID} + dao.GetRow(dao.GetDB(), &good, sql, sqlParams) + retVal.OrderVendorID = good.VendorID return retVal } diff --git a/business/partner/delivery/fn/waybill.go b/business/partner/delivery/fn/waybill.go index dc89467f2..fe4f86bf3 100644 --- a/business/partner/delivery/fn/waybill.go +++ b/business/partner/delivery/fn/waybill.go @@ -221,6 +221,13 @@ func OnWaybillMsg(msg *fnpsapi.OrderStatusNottify) (resp *fnpsapi.CallbackRespon order.StatusTime = time.Now() } order.VendorOrderID, order.OrderVendorID = jxutils.SplitUniversalOrderID(cc.PartnerOrderCode) + + var good *model.GoodsOrder + sql := `SELECT * FROM goods_order WHERE vendor_order_id = ? ORDER BY order_created_at DESC LIMIT 1 OFFSET 0` + sqlParams := []interface{}{cc.PartnerOrderCode} + dao.GetRow(dao.GetDB(), &good, sql, sqlParams) + order.OrderVendorID = good.VendorID + orderStatus, err := strconv.Atoi(order.VendorStatus) if err != nil { globals.SugarLogger.Debugf("FNPS strconv.Atoi fail :[%s]", err) diff --git a/business/partner/delivery/mtps/waybill.go b/business/partner/delivery/mtps/waybill.go index b69b6407f..7f522848b 100644 --- a/business/partner/delivery/mtps/waybill.go +++ b/business/partner/delivery/mtps/waybill.go @@ -182,6 +182,11 @@ func (c *DeliveryHandler) callbackMsg2Waybill(msg *mtpsapi.CallbackOrderMsg) (re Remark: msg.CancelReason, } retVal.VendorOrderID, retVal.OrderVendorID = jxutils.SplitUniversalOrderID(msg.OrderID) + var good *model.GoodsOrder + sql := `SELECT * FROM goods_order WHERE vendor_order_id = ? ORDER BY order_created_at DESC LIMIT 1 OFFSET 0` + sqlParams := []interface{}{msg.OrderID} + dao.GetRow(dao.GetDB(), &good, sql, sqlParams) + retVal.OrderVendorID = good.VendorID return retVal } diff --git a/business/partner/purchase/doudian/doudian.go b/business/partner/purchase/doudian/doudian.go new file mode 100644 index 000000000..353ee408a --- /dev/null +++ b/business/partner/purchase/doudian/doudian.go @@ -0,0 +1,213 @@ +package doudian + +// +//import ( +// "git.rosy.net.cn/jx-callback/business/jxutils/jxcontext" +// "git.rosy.net.cn/jx-callback/business/jxutils/tasksch" +// "git.rosy.net.cn/jx-callback/business/model" +// "git.rosy.net.cn/jx-callback/business/model/dao" +// "git.rosy.net.cn/jx-callback/business/partner" +// "git.rosy.net.cn/jx-callback/business/partner/putils" +// "git.rosy.net.cn/jx-callback/globals/api" +//) +// +//var ( +// CurPurchaseHandler *PurchaseHandler +//) +// +//type PurchaseHandler struct { +// partner.BasePurchasePlatform +// putils.DefSingleStorePlatform +//} +// +//func init() { +// if api.DouDianApi != nil { +// CurPurchaseHandler = New() +// partner.RegisterPurchasePlatform(CurPurchaseHandler) +// } +//} +//func New() (obj *PurchaseHandler) { +// obj = new(PurchaseHandler) +// obj.ISingleStoreStoreSkuHandler = obj +// return obj +//} +// +//func (P *PurchaseHandler) SyncAct(ctx *jxcontext.Context, parentTask tasksch.ITask, act *model.Act2, actOrderRules []*model.ActOrderRule, actStoreSkuList []*model.ActStoreSku2) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) GetActAmple(ctx *jxcontext.Context, vendorStoreID, vendorOrgCode string) (ample int, err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) Map2Order(orderData map[string]interface{}) (order *model.GoodsOrder) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) GetOrder(vendorOrgCode, vendorOrderID, vendorStoreID string) (order *model.GoodsOrder, err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) GetOrderStatus(vendorOrgCode, vendorOrderID string) (status int, err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) AcceptOrRefuseOrder(order *model.GoodsOrder, isAcceptIt bool, userName string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) PickupGoods(order *model.GoodsOrder, isSelfDelivery bool, userName string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) AcceptOrRefuseFailedGetOrder(ctx *jxcontext.Context, order *model.GoodsOrder, isAcceptIt bool) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) CallCourier(ctx *jxcontext.Context, order *model.GoodsOrder) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) ConfirmReceiveGoods(ctx *jxcontext.Context, order *model.GoodsOrder) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) Swtich2SelfDeliver(order *model.GoodsOrder, userName string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) Swtich2SelfDelivered(order *model.GoodsOrder, userName string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) SelfDeliverDelivering(order *model.GoodsOrder, userName string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) GetCancelDeliveryReason(order *model.GoodsOrder) (string, error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) CancelLogisticsByWmOrderId(order *model.GoodsOrder, reasonCode, detailContent, appPoiCode, orderId string) error { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) OrderLogisticsStatus(orderId int64) (int64, error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) SelfDeliverDelivered(order *model.GoodsOrder, userName string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) GetOrderRealMobile(ctx *jxcontext.Context, order *model.GoodsOrder) (mobile string, err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) ReplyOrderComment(ctx *jxcontext.Context, vendorOrgCode string, orderComment *model.OrderComment, replyComment string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) AgreeOrRefuseCancel(ctx *jxcontext.Context, order *model.GoodsOrder, isAgree bool, reason string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) CancelOrder(ctx *jxcontext.Context, order *model.GoodsOrder, reason string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) AdjustOrder(ctx *jxcontext.Context, order *model.GoodsOrder, removedSkuList []*model.OrderSku, reason string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) RefundOrder(ctx *jxcontext.Context, order *model.GoodsOrder, reason string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) PartRefundOrder(ctx *jxcontext.Context, order *model.GoodsOrder, refundSkuList []*model.OrderSku, reason string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) AgreeOrRefuseRefund(ctx *jxcontext.Context, order *model.AfsOrder, approveType int, reason string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) ConfirmReceivedReturnGoods(ctx *jxcontext.Context, order *model.AfsOrder) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) GetSelfTakeCode(ctx *jxcontext.Context, order *model.GoodsOrder) (code string, err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) ConfirmSelfTake(ctx *jxcontext.Context, order *model.GoodsOrder, selfTakeCode string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) GetOrderAfsInfo(ctx *jxcontext.Context, vendorOrderID, afsOrderID string) (orderAfsInfo *partner.OrderAfsInfo, err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) ComplaintRider(vendorOrderId string, resonID int, resonContent string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) GetOrderRider(vendorOrgCode, vendorStoreID string, param map[string]interface{}) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) GetVendorID() int { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) GetVendorCategories(ctx *jxcontext.Context) (vendorCats []*model.SkuVendorCategory, err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) DeleteStore(db *dao.DaoDB, storeID int, userName string) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) UpdateStoreCustomID(ctx *jxcontext.Context, vendorOrgCode, vendorStoreID string, storeID int64) (err error) { +// //TODO implement me +// panic("implement me") +//} +// +//func (P *PurchaseHandler) UploadImg(ctx *jxcontext.Context, vendorOrgCode, imgURL string, imgData []byte, imgName string, imgType int) (imgHint string, err error) { +// //TODO implement me +// panic("implement me") +//} diff --git a/business/partner/purchase/doudian/store.go b/business/partner/purchase/doudian/store.go new file mode 100644 index 000000000..2063333cb --- /dev/null +++ b/business/partner/purchase/doudian/store.go @@ -0,0 +1,428 @@ +package doudian + +// +//import ( +// "errors" +// "fmt" +// address_create_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/address_create/request" +// address_list_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/address_list/request" +// address_list_response "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/address_list/response" +// freightTemplate_create_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/freightTemplate_create/request" +// shop_batchCreateStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_batchCreateStore/request" +// shop_bindStoreFreight_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_bindStoreFreight/request" +// shop_bindStoreSaleLimit_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_bindStoreSaleLimit/request" +// shop_editStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_editStore/request" +// shop_getStoreDetail_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_getStoreDetail/request" +// shop_getStoreList_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_getStoreList/request" +// shop_storeSuspend_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_storeSuspend/request" +// shop_unsuspendStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_unsuspendStore/request" +// trade_createTradeLimitTemplate_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/trade_createTradeLimitTemplate/request" +// "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/tiktok_api" +// "git.rosy.net.cn/baseapi/utils" +// "git.rosy.net.cn/baseapi/utils/errlist" +// "git.rosy.net.cn/jx-callback/business/jxstore/event" +// "git.rosy.net.cn/jx-callback/business/jxutils" +// "git.rosy.net.cn/jx-callback/business/jxutils/jxcontext" +// "git.rosy.net.cn/jx-callback/business/jxutils/tasksch" +// "git.rosy.net.cn/jx-callback/business/model" +// "git.rosy.net.cn/jx-callback/business/model/dao" +// "git.rosy.net.cn/jx-callback/globals" +// "git.rosy.net.cn/jx-callback/globals/api" +//) +// +//func splicingTimeToDoudian(openTime1, closeTime1, openTime2, closeTime2 int16) (timeList string) { +// //700 1200 -> 7:00-12:00 +// timeStr := "" +// if openTime1 != 0 && closeTime1 != 0 { +// tOpenTime1 := utils.Int64ToStr(int64(openTime1)) +// len1 := len(tOpenTime1) - 2 +// s1 := tOpenTime1[:len1] + ":" + tOpenTime1[len1+1:] +// tCloseTime1 := utils.Int64ToStr(int64(closeTime1)) +// len2 := len(tCloseTime1) - 2 +// s2 := tCloseTime1[:len2] + ":" + tCloseTime1[len2+1:] +// timeStr += s1 + "-" + s2 +// if openTime2 != 0 && closeTime2 != 0 { +// tOpenTime2 := utils.Int64ToStr(int64(openTime2)) +// len3 := len(tOpenTime2) - 2 +// s3 := tOpenTime2[:len3] + ":" + tOpenTime2[len3+1:] +// tCloseTime2 := utils.Int64ToStr(int64(closeTime2)) +// len4 := len(tCloseTime2) - 2 +// s4 := tCloseTime2[:len4] + ":" + tCloseTime2[len4+1:] +// timeStr += " " + s3 + "-" + s4 +// } +// } +// return timeStr +//} +// +//// shop/batchCreateStore 批量创建门店 +//func (P *PurchaseHandler) CreateStore2(db *dao.DaoDB, storeID int, userName string, params map[string]interface{}, storeDetail *dao.StoreDetail) (vendorStoreID string, err error) { +// var ( +// storeIDs string +// lists []shop_batchCreateStore_request.StoreListItem +// ShopBatchCreateStoreParam *shop_batchCreateStore_request.ShopBatchCreateStoreParam +// ) +// timeStr := "" +// if storeDetail.OpenTime1 == 0 || storeDetail.CloseTime1 == 0 { +// return "", fmt.Errorf("营业时间必填") +// } else { +// timeStr = splicingTimeToDoudian(storeDetail.OpenTime1, storeDetail.CloseTime1, storeDetail.OpenTime2, storeDetail.CloseTime2) +// } +// m := make(map[int64]string) +// for j := 1; j <= 7; j++ { +// m[int64(j)] = timeStr +// } +// list := shop_batchCreateStore_request.StoreListItem{ +// RowId: 1, +// Name: storeDetail.Name, +// StoreCode: storeDetail.VendorStoreID, +// Longitude: utils.Float64ToStr(jxutils.IntCoordinate2Standard(storeDetail.Lng)), +// Latitude: utils.Float64ToStr(jxutils.IntCoordinate2Standard(storeDetail.Lat)), +// Province: storeDetail.ProvinceName, +// City: storeDetail.CityName, +// District: storeDetail.DistrictName, +// Address: storeDetail.Address, +// Contact: storeDetail.Tel1, +// OpenTime: &shop_batchCreateStore_request.OpenTime{ +// DayMap: m, +// }, +// } +// lists = append(lists, list) +// ShopBatchCreateStoreParam = &shop_batchCreateStore_request.ShopBatchCreateStoreParam{ +// StoreList: lists, +// } +// if resp, err := api.DouDianApi.BatchCreateStore(ShopBatchCreateStoreParam); err != nil { +// return "", err +// } else { +// for k, v := range resp.ResultList { +// if k != len(resp.ResultList) { +// storeIDs += utils.Int64ToStr(v.Store.StoreId) + "," +// } +// storeIDs += utils.Int64ToStr(v.Store.StoreId) +// } +// return storeIDs, nil +// } +//} +// +//// shop/editStore 编辑门店信息 正向推送平台 +//func (P *PurchaseHandler) UpdateStore(db *dao.DaoDB, storeID int, userName string) (err error) { +// globals.SugarLogger.Debugf("doudian Update storeID:%d, userName:%s", storeID, userName) +// var ( +// storeInfo *dao.StoreDetail +// name string +// ) +// if db == nil { +// db = dao.GetDB() +// } +// sqlStr := ` SELECT +// t1.*, +// t2.status, t2.vendor_store_id, t2.vendor_org_code, +// IF(t1.updated_at > t2.updated_at, t1.last_operator, t2.last_operator) real_last_operator, t2.sync_status, t2.vendor_store_name +// FROM store t1 +// LEFT JOIN store_map t2 ON t1.id = t2.store_id AND t2.vendor_id = ? AND (t2.deleted_at = ?) +// WHERE t1.id = ? +// ORDER BY t2.updated_at` +// err = dao.GetRow(db, &storeInfo, sqlStr, model.VendorIDDouDian, utils.DefaultTimeValue, utils.Int2Str(storeID)) +// if err != nil { +// return err +// } +// errList := errlist.New() +// timeStr := "" +// m := make(map[int64]string) +// if storeInfo.OpenTime1 != 0 && storeInfo.CloseTime1 != 0 { +// timeStr = splicingTimeToDoudian(storeInfo.OpenTime1, storeInfo.CloseTime1, storeInfo.OpenTime2, storeInfo.CloseTime2) +// for j := 1; j <= 7; j++ { +// m[int64(j)] = timeStr +// } +// } +// vendorStoreID := &shop_getStoreDetail_request.ShopGetStoreDetailParam{ +// StoreId: utils.Str2Int64(storeInfo.VendorStoreID), +// } +// if globals.EnableDdStoreWrite { +// remoteStoreInfo, err2 := api.DouDianApi.GetStoreDetail(vendorStoreID) +// if err2 != nil { +// return err2 +// } +// if remoteStoreInfo.StoreDetail.Store.StoreId == 0 { +// return fmt.Errorf("ID:%d 的门店不存在,请先创建", utils.Str2Int64(storeInfo.VendorStoreID)) +// } +// mergedStoreStatus := jxutils.MergeStoreStatus(storeInfo.Status, storeInfo.VendorStatus) +// name = remoteStoreInfo.StoreDetail.Store.Name +// if storeInfo.SyncStatus&(model.SyncFlagNewMask|model.SyncFlagStoreName) != 0 { +// if storeInfo.VendorStoreName != "" { +// name = storeInfo.VendorStoreName +// } +// } +// store := fmt.Sprintf("门店id:%d,门店名称:%s,第三方门店状态:%d,本地修改前门店状态%d,本地门店修改后状态:%d,第三方平台Id(抖店):%s", storeID, remoteStoreInfo.StoreDetail.Store.Name, remoteStoreInfo.StoreDetail.Store.State, storeInfo.Status, mergedStoreStatus, storeInfo.VendorOrgCode) +// event.AddOperateEvent(jxcontext.AdminCtx, jxcontext.AdminCtx.GetTrackInfo(), store, "", "", 10, "UpdateStore") +// params := &shop_editStore_request.ShopEditStoreParam{ +// StoreId: remoteStoreInfo.StoreDetail.Store.StoreId, //平台id不可修改 +// Name: name, +// StoreCode: utils.Int2Str(storeInfo.ID), //自用编码即很本地storeID +// Latitude: utils.Int2Str(storeInfo.Lat), +// Longitude: utils.Int2Str(storeInfo.Lng), +// Province: storeInfo.ProvinceName, +// City: storeInfo.CityName, +// District: storeInfo.DistrictName, +// Address: storeInfo.Address, +// Contact: storeInfo.Tel1, +// OpenTime: &shop_editStore_request.OpenTime{ +// DayMap: m, +// }, +// } +// //修改店铺状态 +// if storeInfo.SyncStatus&(model.SyncFlagNewMask|model.SyncFlagStoreStatus) != 0 { +// errList.AddErr(P.UpdateStoreStatus(jxcontext.AdminCtx, storeInfo.VendorOrgCode, storeID, storeInfo.VendorStoreID, mergedStoreStatus)) +// } +// _, err3 := api.DouDianApi.EditStore(params) +// if err3 != nil { +// errList.AddErr(err3) +// } +// } +// return err +//} +// +//// shop/storeSuspend 门店暂停营业 +//// shop/unsuspendStore 门店恢复营业 +//func (p *PurchaseHandler) UpdateStoreStatus(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, status int) (err error) { +// isOnline := bizStatusJX2DouDian(status) +// if globals.EnableDdStoreWrite { +// if isOnline != tiktok_api.StoreStatusOnline { //暂停营业状态 +// unsuspendStoreID := &shop_unsuspendStore_request.ShopUnsuspendStoreParam{ +// StoreId: utils.Str2Int64(vendorStoreID), +// } +// _, err = api.DouDianApi.UnsuspendStore(unsuspendStoreID) +// } else { //恢复营业 +// suspendStoreID := &shop_storeSuspend_request.ShopStoreSuspendParam{ +// StoreId: utils.Str2Int64(vendorStoreID), +// } +// getStoreID := &shop_getStoreDetail_request.ShopGetStoreDetailParam{ +// StoreId: utils.Str2Int64(vendorStoreID), +// } +// //平台上店铺状态 +// remoteStoreInfo, err2 := api.DouDianApi.GetStoreDetail(getStoreID) +// if err2 != nil { +// return err2 +// } +// if remoteStoreInfo.StoreDetail.Store.SuspendType == tiktok_api.SuspendTypePlatformPenalty { +// err = errors.New("门店因平台处罚暂停营业,不可主动修改营业状态") +// } else { +// _, err = api.DouDianApi.StoreSuspend(suspendStoreID) +// } +// } +// } +// return err +//} +// +//// /freightTemplate/create 创建运费模板 +//func (P *PurchaseHandler) CreateFreightTemplate(templateInfo freightTemplate_create_request.FreightTemplateCreateParam, storeID, vendorStoreID int64) error { +// var ( +// db *dao.DaoDB +// ) +// if templateInfo.Template.RuleType > 0 { +// templateInfo.Template.CalculateType = tiktok_api.CalculateTypeNum +// } +// info := &freightTemplate_create_request.FreightTemplateCreateParam{ +// Template: templateInfo.Template, +// Columns: templateInfo.Columns, +// } +// resp, err := api.DouDianApi.FreightTemplateCreate(info) +// if err != nil { +// return err +// } +// //创建成功后进行绑定 +// bindInfo := &shop_bindStoreFreight_request.ShopBindStoreFreightParam{ +// StoreId: vendorStoreID, +// FreightId: resp.TemplateId, +// } +// _, err1 := api.DouDianApi.BindFreightTemplate(bindInfo) +// if err != nil { +// return err1 +// } +// //并写入数据库 +// freightInfo := model.FreightTemplate{ +// StoreID: storeID, +// VendorStoreID: vendorStoreID, +// TemplateID: resp.TemplateId, +// } +// if err = dao.CreateEntity(db, freightInfo); err != nil { +// return err +// } +// return nil +//} +// +//// /shop/bindStoreFreight 门店绑定运费模版 +////门店绑定运费模版,运费模版必须属于门店关联的抖店,且门店与运费模版是一对一关系 +//func (P *PurchaseHandler) ShopBindStoreFreight(storeID, freightID int64) error { +// param := &shop_bindStoreFreight_request.ShopBindStoreFreightParam{ +// StoreId: storeID, +// FreightId: freightID, +// } +// _, err := api.DouDianApi.BindFreightTemplate(param) +// if err != nil { +// return err +// } +// return nil +//} +// +//// /address/create 创建店铺地址库(新建即绑定) +//func (P *PurchaseHandler) CreateAddress(addressInfo address_create_request.AddressCreateParam) (addressID int64, err error) { +// info := &address_create_request.AddressCreateParam{ +// Address: addressInfo.Address, +// StoreId: addressInfo.StoreId, +// } +// resp, err := api.DouDianApi.AddressCreate(info) +// if err != nil { +// return 0, err +// } +// //添加进数据库page_shop +// //获取门店信息 +// //storeID := &shop_getStoreDetail_request.ShopGetStoreDetailParam{ +// // StoreId: addressInfo.StoreId, +// //} +// //storeInfo, err1 := api.DouDianApi.GetStoreDetail(storeID) +// //if err1 != nil { +// // return 0, err1 +// //} +// //createAddress := &model.PageShop{ //此表暂存门店售后地址库 +// // Name: storeInfo.StoreDetail.Store.Name, +// // VendorID: model.VendorIDDouDian, +// // VendorStoreID: utils.Int64ToStr(storeInfo.StoreDetail.Store.StoreId), //抖店平台ID +// // OrgCode: storeInfo.StoreDetail.Store.StoreCode, //暂时用来存放京西平台门店ID +// // VendorStatus: utils.Int64ToStr(storeInfo.StoreDetail.Store.State), +// // Status: 0, +// // CityCode: utils.Str2Int(storeInfo.StoreDetail.Store.CityCode), +// // DistrictCode: utils.Str2Int(storeInfo.StoreDetail.Store.DistrictCode), +// // Address: storeInfo.StoreDetail.Store.Address, +// // Lng: utils.Str2Float64(storeInfo.StoreDetail.Store.Longitude), +// // Lat: utils.Str2Float64(storeInfo.StoreDetail.Store.Latitude), +// // Tel1: storeInfo.StoreDetail.Store.Contact, +// //} +// //if err = dao.CreateEntity(dao.GetDB(), createAddress); err != nil { +// // return 0, err +// //} +// return resp.AddressId, nil +//} +// +//// /address/list 获取售后地址列表接口 +////分页获取商家地址列表 +//func (P *PurchaseHandler) GetAddressList(param *address_list_request.AddressListParam) (*address_list_response.AddressListData, error) { +// //不传入ID则是获取所有门店售后地址列表 +// info := &address_list_request.AddressListParam{ +// PageSize: 10, +// PageNo: 1, +// OrderBy: param.OrderBy, +// OrderField: param.OrderField, +// } +// if param.StoreId != 0 { +// info.StoreId = param.StoreId +// } +// listInfo, err := api.DouDianApi.GetAddressList(info) +// if err != nil { +// return nil, err +// } +// return listInfo, nil +//} +// +//// /trade/createTradeLimitTemplate 创建限售模板 +//func (P *PurchaseHandler) CreateTradeLimitTemplate(template trade_createTradeLimitTemplate_request.TradeCreateTradeLimitTemplateParam) (tradeLimitID int64, err error) { +// info := &trade_createTradeLimitTemplate_request.TradeCreateTradeLimitTemplateParam{ +// StoreId: template.StoreId, +// TradeLimitRuleRequestList: template.TradeLimitRuleRequestList, +// } +// resp, err := api.DouDianApi.CreateTradeLimitTemplate(info) +// if err != nil { +// return 0, err +// } +// return resp.TradeLimitId, nil +//} +// +//// /shop/bindStoreSaleLimit 门店绑定限售模板 +//func (P *PurchaseHandler) BindStoreSaleLimit(storeID, saleLimitTemplateID int64) error { +// info := &shop_bindStoreSaleLimit_request.ShopBindStoreSaleLimitParam{ +// StoreId: storeID, +// SaleLimitId: saleLimitTemplateID, +// } +// if _, err := api.DouDianApi.BindStoreSaleLimit(info); err != nil { +// return err +// } +// return nil +//} +// +//func (P *PurchaseHandler) UpdateStoreOpTime(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, opTimeList []int16) (err error) { +// t1 := opTimeList[0] +// t2 := opTimeList[1] +// t3 := opTimeList[2] +// t4 := opTimeList[4] +// timeStr := splicingTimeToDoudian(t1, t2, t3, t4) +// m := make(map[int64]string) +// for j := 1; j <= 7; j++ { +// m[int64(j)] = timeStr +// } +// params := &shop_editStore_request.ShopEditStoreParam{ +// StoreId: utils.Str2Int64(vendorStoreID), +// OpenTime: &shop_editStore_request.OpenTime{ +// DayMap: m, +// }, +// } +// if globals.EnableDdStoreWrite { +// api.DouDianApi.EditStore(params) +// } +// return err +//} +// +//func (P *PurchaseHandler) GetStoreStatus(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string) (storeStatus int, err error) { +// params := &shop_getStoreDetail_request.ShopGetStoreDetailParam{ +// StoreId: utils.Str2Int64(vendorStoreID), +// } +// result, err := api.DouDianApi.GetStoreDetail(params) +// if err != nil { +// return 0, err +// } +// status := bizStatusJX2DouDian(int(result.StoreDetail.Store.State)) +// return status, nil +//} +// +//func (P *PurchaseHandler) EnableAutoAcceptOrder(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, isSetEnable bool) (err error) { +// return err +//} +// +//// 获取店铺所有平台ID +//func (P *PurchaseHandler) GetAllStoresVendorID(ctx *jxcontext.Context, vendorOrgCode string) (vendorStoreIDs []string, err error) { +// param := &shop_getStoreList_request.ShopGetStoreListParam{ +// Page: 0, +// PageSize: 10, +// } +// storeList, err := api.DouDianApi.GetStoreList(param) +// if err != nil { +// return nil, err +// } +// if len(storeList.StoreDetailList) > 0 { +// vendorStoreIDs = make([]string, len(storeList.StoreDetailList)) +// for k, v := range storeList.StoreDetailList { +// vendorStoreIDs[k] = utils.Int64ToStr(v.Store.StoreId) +// } +// } +// return vendorStoreIDs, err +//} +// +//func (P *PurchaseHandler) UpdateStoreLineStatus(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, lineStatus int) (err error) { +// if lineStatus == model.StoreStatusOpened { +// param := &shop_storeSuspend_request.ShopStoreSuspendParam{ +// StoreId: utils.Str2Int64(vendorStoreID), +// } +// _, err = api.DouDianApi.StoreSuspend(param) +// } else { +// param := &shop_unsuspendStore_request.ShopUnsuspendStoreParam{ +// StoreId: utils.Str2Int64(vendorStoreID), +// } +// _, err = api.DouDianApi.UnsuspendStore(param) +// } +// return err +//} +//func (P *PurchaseHandler) ReadStore(ctx *jxcontext.Context, vendorOrgCode, vendorStoreID, vendorStoreName string) (store *dao.StoreDetail, err error) { +// return nil, err +//} +// +//func (P *PurchaseHandler) RefreshAllStoresID(ctx *jxcontext.Context, parentTask tasksch.ITask, isAsync bool) (hint string, err error) { +// return "", errors.New("抖店暂不支持此操作") +//} diff --git a/business/partner/purchase/doudian/store_test.go b/business/partner/purchase/doudian/store_test.go new file mode 100644 index 000000000..3830917cb --- /dev/null +++ b/business/partner/purchase/doudian/store_test.go @@ -0,0 +1,109 @@ +package doudian + +// +//import ( +// freightTemplate_create_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/freightTemplate_create/request" +// shop_batchCreateStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_batchCreateStore/request" +// "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/tiktok_api" +// "git.rosy.net.cn/baseapi/utils" +// "git.rosy.net.cn/jx-callback/business/model" +// "git.rosy.net.cn/jx-callback/business/model/dao" +// "testing" +//) +// +//func TestCreateStore(t *testing.T) { +// accesstoken := `{"access_token":"90868a42-1287-4453-ba71-34c72f22e886","expires_in":555553,"scope":"SCOPE","shop_id":"","shop_name":"小时达开放平台对接专用店","refresh_token":"4e8cf946-8df1-4489-be88-f96f2d4603a8","authority_id ":""}` +// tiktok_api.New("7136048270014416392", "c397aa9f-3927-47c4-8cfe-4d84e02602e0", accesstoken) +// request := shop_batchCreateStore_request.New() +// //storeList := make([]*shop_batchCreateStore_request.StoreListItem, 0) +// storeInfo := model.Store{ +// Name: "京西菜市小时达测试店铺0926", +// Lng: utils.Str2Int("128.443241"), +// Lat: utils.Str2Int("31.133237"), +// Address: "金牛区一环路北二段10号", +// Tel1: "17358644830", +// OpenTime1: 700, +// CloseTime1: 1230, +// OpenTime2: 1300, +// CloseTime2: 1800, +// //OpenTime: map[int64]string{1: "07:00-19:00", 2: "8:00-19:00"}, +// } +// list := &dao.StoreDetail{} +// list.Store = storeInfo +// list.ProvinceName = "四川省" +// list.CityName = "成都市" +// list.DistrictName = "金牛区" +// list.VendorStoreID = "666667" +// _, err := CurPurchaseHandler.CreateStore2(nil, 0, "", nil, list) +// resp, err := request.Execute(tiktok_api.AccessToken) +// t.Fatal("err===========", err) +// t.Fatalf("resp===========:%v", resp) +//} +// +//func TestUpdateStore(t *testing.T) { +// accesstoken := `{"access_token":"90868a42-1287-4453-ba71-34c72f22e886","expires_in":555553,"scope":"SCOPE","shop_id":"","shop_name":"小时达开放平台对接专用店","refresh_token":"4e8cf946-8df1-4489-be88-f96f2d4603a8","authority_id ":""}` +// tiktok_api.New("7136048270014416392", "c397aa9f-3927-47c4-8cfe-4d84e02602e0", accesstoken) +// request := shop_batchCreateStore_request.New() +// err := CurPurchaseHandler.UpdateStore(nil, 666667, "") +// resp, err := request.Execute(tiktok_api.AccessToken) +// t.Fatal("err===========", err) +// t.Fatalf("resp===========:%v", resp) +//} +//// +////func TestCreateFreightTemplate(t *testing.T) { +//// accesstoken := `{"access_token":"6c4d71b3-831c-4a96-8d2e-977e37afba5a","expires_in":462248,"scope":"SCOPE","shop_id":"","shop_name":"小时达开放平台对接 专用店","refresh_token":"65aae144-4cc0-44d2-89ba-5d3062caca41","authority_ id":""}` +//// tiktok_api.New("7136048270014416392", "c397aa9f-3927-47c4-8cfe-4d84e02602e0", accesstoken) +//// t1 := freightTemplate_create_request.FreightTemplateCreateParam{ +//// Columns: []freightTemplate_create_request.ColumnsItem{ +//// { +//// AddWeight: 20, +//// MinSkuAmount: -1, +//// FirstWeight: 20, +//// ProvinceInfos: []freightTemplate_create_request.ProvinceInfosItem{ +//// { +//// Id: 51, +//// Children: []freightTemplate_create_request.ChildrenItem_4{ +//// { +//// Id: 510101, +//// Children: []freightTemplate_create_request.ChildrenItem_5{ +//// { +//// Id: 510107, +//// Children: []freightTemplate_create_request.ChildrenItem{ +//// { +//// Id: 610041, +//// }, +//// }, +//// }, +//// }, +//// }, +//// }, +//// }, +//// }, +//// }, +//// }, +//// Template: &freightTemplate_create_request.Template{ +//// TemplateName: "运费模板创建测试0929", +//// ProductProvince: 51, +//// ProductCity: 510104, +//// CalculateType: 1, +//// TransferType: 1, +//// RuleType: 0, +//// }, +//// } +//// //t2 := []freightTemplate_create_request.FreightTemplateCreateParam{} +//// //t2 = append(t2, t1) +//// freightID, err := CurPurchaseHandler.CreateFreightTemplate(t1) +//// //fmt.Println("freightID==", fmt.Sprintf("%v", freightID)) +//// t.Fatal("err===========", err) +//// t.Fatalf("resp===========:%v", freightID) +////} +// +////func TestBindFreightTemplate(t *testing.T) { +//// accesstoken := `{"access_token":"6c4d71b3-831c-4a96-8d2e-977e37afba5a","expires_in":462248,"scope":"SCOPE","shop_id":"","shop_name":"小时达开放平台对接 专用店","refresh_token":"65aae144-4cc0-44d2-89ba-5d3062caca41","authority_ id":""}` +//// tiktok_api.New("7136048270014416392", "c397aa9f-3927-47c4-8cfe-4d84e02602e0", accesstoken) +//// request := shop_bindStoreFreight_request.New() +//// param := shop_bindStoreFreight_request.ShopBindStoreFreightParam{ +//// //StoreId: , +//// //FreightId: , +//// } +////} diff --git a/business/partner/purchase/doudian/warehouse.go b/business/partner/purchase/doudian/warehouse.go new file mode 100644 index 000000000..d57bd3ed8 --- /dev/null +++ b/business/partner/purchase/doudian/warehouse.go @@ -0,0 +1,143 @@ +package doudian + +//import ( +// "fmt" +// warehouse_bindFencesByStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/warehouse_bindFencesByStore/request" +// warehouse_bindStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/warehouse_bindStore/request" +// warehouse_createBatch_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/warehouse_createBatch/request" +// warehouse_createFence_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/warehouse_createFence/request" +// "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/tiktok_api" +// "git.rosy.net.cn/baseapi/utils" +// "git.rosy.net.cn/jx-callback/business/model" +// "git.rosy.net.cn/jx-callback/business/model/dao" +// "git.rosy.net.cn/jx-callback/globals/api" +// "strings" +//) +// +//// /warehouse/createBatch 批量创建区域仓 +//func (P *PurchaseHandler) BatchCreateWarehouse(param warehouse_createBatch_request.WarehouseCreateBatchParam) error { +// infos := []warehouse_createBatch_request.OutWarehouseListItem{} +// for _, v := range param.OutWarehouseList { +// info := warehouse_createBatch_request.OutWarehouseListItem{ +// OutWarehouseId: v.OutWarehouseId, +// Name: v.Name, +// Intro: v.Intro, +// AddressDetail: v.AddressDetail, +// WarehouseLocation: v.WarehouseLocation, +// } +// infos = append(infos, info) +// } +// req := &warehouse_createBatch_request.WarehouseCreateBatchParam{ +// OutWarehouseList: infos, +// } +// resp, err := api.DouDianApi.BatchCreateWarehouse(req) +// if err != nil { +// return err +// } +// if resp.Data["outWarehouseId"] == false { +// return fmt.Errorf("outWarehouseId:%v 出错", resp.Data["outWarehouseId"]) +// } +// return nil +//} +// +//// /warehouse/bindStore 仓库绑定门店 +//func (P *PurchaseHandler) BindStoreWarehouse(storeIDs []int64, outWarehouseID string) error { +// param := &warehouse_bindStore_request.WarehouseBindStoreParam{ +// StoreIds: storeIDs, +// OutWarehouseId: outWarehouseID, +// } +// if _, err := api.DouDianApi.StoreBindWarehouse(param); err != nil { +// return err +// } +// return nil +//} +// +//type LocalStore struct { +// Lng int `json:"-"` // 乘了10的6次方 +// Lat int `json:"-"` // 乘了10的6次方 +// DeliveryRangeType int8 `json:"deliveryRangeType"` // 参见相关常量定义 +// DeliveryRange string `json:"deliveryRange"` // 如果DeliveryRangeType为DeliveryRangeTypePolygon,则为逗号分隔坐标,分号分隔的坐标点(坐标与Lng和Lat一样,都是整数),比如 121361504,31189308;121420555,31150238。否则为半径,单位为米 +// VendorStoreID string `json:"vendorStoreID"` // 平台上门店id +//} +// +//// /warehouse/createFence 以门店方式创建电子围栏 +//func (P *PurchaseHandler) CreateFenceByStore(storeID int) (fenceID string, err error) { +// var ( +// db *dao.DaoDB +// localStore *LocalStore +// verticeses []warehouse_createFence_request.VerticesItem +// ) +// sqlParam := []interface{}{ +// model.VendorIDDouDian, +// } +// sqlStr := ` SELECT t.lng,t.lat,t.delivery_range_type,t.delivery_range,s.vendor_store_id FROM store t +// LEFT JOIN store_map s ON t.id = s.store_id +// WHERE s.vendor_id= ? ` +// if storeID != 0 { +// sqlStr += " AND t.id = ? " +// sqlParam = append(sqlParam, storeID) +// } else { +// return "", fmt.Errorf("storeID必填") +// } +// if err = dao.GetRow(db, &localStore, sqlStr, sqlParam...); err == nil { +// param := &warehouse_createFence_request.WarehouseCreateFenceParam{ +// FenceInfo: &warehouse_createFence_request.FenceInfo{ +// OutFenceId: "京西门店:" + utils.Int2Str(storeID) + " 的电子围栏", +// Shape: int32(localStore.DeliveryRangeType), +// }, +// } +// if localStore.DeliveryRangeType == tiktok_api.ShapeCircular { +// circular := &warehouse_createFence_request.Circular{ +// Center: &warehouse_createFence_request.Center{ +// Longitude: utils.Int2Float64(localStore.Lng), +// Latitude: utils.Int2Float64(localStore.Lat), +// }, +// Radius: utils.Str2Float64(localStore.DeliveryRange), +// } +// param.FenceInfo.Circular = circular +// } else if localStore.DeliveryRangeType == tiktok_api.ShapePolygon { +// tempStr := strings.Split(localStore.DeliveryRange, ";") +// for v := len(tempStr) - 1; v >= 0; v-- { +// s2 := strings.Split(tempStr[v], ",") +// vertices := warehouse_createFence_request.VerticesItem{ +// Longitude: utils.Str2Float64(s2[0]), +// Latitude: utils.Str2Float64(s2[1]), +// } +// verticeses = append(verticeses, vertices) +// } +// param.FenceInfo.Polygon.Vertices = verticeses +// } +// resp, err := api.DouDianApi.CreateFence(param) +// if err != nil { +// return "", err +// } else { +// return resp.FenceId, err +// } +// } else { +// return "", err +// } +//} +// +////直接创建电子围栏方式 +//func (P *PurchaseHandler) CreateFenceDirectly(param warehouse_createFence_request.WarehouseCreateFenceParam) (fenceID string, err error) { +// info := &warehouse_createFence_request.WarehouseCreateFenceParam{ +// FenceInfo: param.FenceInfo, +// } +// resp, err := api.DouDianApi.CreateFence(info) +// if err != nil { +// return "", err +// } +// return resp.FenceId, err +//} +// +////门店直接绑定围栏 +//func (P *PurchaseHandler) BindFenceByStore(storeID int64, addOutFenceIDs []string) error { +// param := &warehouse_bindFencesByStore_request.WarehouseBindFencesByStoreParam{ +// StoreId: storeID, +// AddOutFenceIds: addOutFenceIDs, +// } +// if _, err := api.DouDianApi.BindFenceByStore(param); err != nil { +// return err +// } +// return nil +//} diff --git a/business/partner/purchase/ebai/store.go b/business/partner/purchase/ebai/store.go index b926a954e..276fd9f0a 100644 --- a/business/partner/purchase/ebai/store.go +++ b/business/partner/purchase/ebai/store.go @@ -255,8 +255,7 @@ func (p *PurchaseHandler) UpdateStore(db *dao.DaoDB, storeID int, userName strin JOIN store_map t2 ON t1.id = t2.store_id AND t2.vendor_id = ? AND (t2.deleted_at = ?) LEFT JOIN brand t3 ON t3.id = t1.brand_id WHERE t1.id = ? - ORDER BY t2.updated_at - ` + ORDER BY t2.updated_at` if err = dao.GetRows(db, &stores, sql, model.VendorIDEBAI, utils.DefaultTimeValue, storeID); err == nil { for _, store := range stores { if globals.EnableEbaiStoreWrite { @@ -264,7 +263,7 @@ func (p *PurchaseHandler) UpdateStore(db *dao.DaoDB, storeID int, userName strin if store.SyncStatus&model.SyncFlagDeletedMask == 0 { shopID = store.ID } - store2, err2 := p.ReadStore(jxcontext.AdminCtx, store.VendorOrgCode, store.VendorStoreID,"") + store2, err2 := p.ReadStore(jxcontext.AdminCtx, store.VendorOrgCode, store.VendorStoreID, "") // globals.SugarLogger.Debugf("ebai UpdateStore2 store2:%s, err2:%v", utils.Format4Output(store2, true), err2) if err = err2; err == nil { if store2.ID == store.ID { diff --git a/business/partner/purchase/ebai/store_test.go b/business/partner/purchase/ebai/store_test.go index c24f5ba3b..c9972dc8b 100644 --- a/business/partner/purchase/ebai/store_test.go +++ b/business/partner/purchase/ebai/store_test.go @@ -3,19 +3,16 @@ package ebai import ( "testing" - "git.rosy.net.cn/jx-callback/business/jxutils/jxcontext" - - "git.rosy.net.cn/baseapi/utils" "git.rosy.net.cn/jx-callback/business/model/dao" ) -func TestReadStore(t *testing.T) { - result, err := CurPurchaseHandler.ReadStore(jxcontext.AdminCtx, "", testShopBaiduID) - if err != nil { - t.Fatal(err.Error()) - } - t.Log(utils.Format4Output(result, false)) -} +//func TestReadStore(t *testing.T) { +// result, err := CurPurchaseHandler.ReadStore(jxcontext.AdminCtx, "", testShopBaiduID) +// if err != nil { +// t.Fatal(err.Error()) +// } +// t.Log(utils.Format4Output(result, false)) +//} func TestUpdateStore(t *testing.T) { db := dao.GetDB() diff --git a/business/partner/purchase/mtwm/store.go b/business/partner/purchase/mtwm/store.go index 79f000d59..b6767b62f 100644 --- a/business/partner/purchase/mtwm/store.go +++ b/business/partner/purchase/mtwm/store.go @@ -61,7 +61,7 @@ type tEbaiStoreInfo struct { DistrictID int `orm:"column(district_id)"` } -func (p *PurchaseHandler) ReadStore(ctx *jxcontext.Context, vendorOrgCode, vendorStoreID,vendorStoreName string) (retVal *dao.StoreDetail, err error) { +func (p *PurchaseHandler) ReadStore(ctx *jxcontext.Context, vendorOrgCode, vendorStoreID, vendorStoreName string) (retVal *dao.StoreDetail, err error) { result, err := getAPIWithoutToken(vendorOrgCode).PoiGet(vendorStoreID) if err == nil { // globals.SugarLogger.Debug(utils.Format4Output(result, false)) @@ -232,12 +232,13 @@ func (p *PurchaseHandler) UpdateStore(db *dao.DaoDB, storeID int, userName strin db = dao.GetDB() } mtapi := getAPI(getStoreVendorOrgCode(storeID), storeID, "") + //获取本地store信息 storeDetail, err := dao.GetStoreDetail(db, storeID, model.VendorIDMTWM, "") if err != nil { return err } errList := errlist.New() - + //获取平台store信息 remoteStoreInfo, err := mtapi.PoiGet(storeDetail.VendorStoreID) if err != nil { return err diff --git a/business/partner/purchase/tiktok_store/financial_test.go b/business/partner/purchase/tiktok_store/financial_test.go index b055fd09c..038bb2699 100644 --- a/business/partner/purchase/tiktok_store/financial_test.go +++ b/business/partner/purchase/tiktok_store/financial_test.go @@ -8,7 +8,6 @@ import ( "git.rosy.net.cn/baseapi/platformapi/mtwmapi" "git.rosy.net.cn/baseapi/utils" - "git.rosy.net.cn/jx-callback/business/partner" ) func TestOnFinancialMsg(t *testing.T) { @@ -41,14 +40,14 @@ func TestOnFinancialMsg(t *testing.T) { }, } msg.FormData.Set("food", string(utils.MustMarshal(food))) - res := CurPurchaseHandler.onAfsOrderMsg(msg) + res := CurPurchaseHandler.onAfsOrderMsg("1", msg) fmt.Println(res) } -func TestOnOrderDetail(t *testing.T) { - result := map[string]interface{}{ - "app_order_code": "", "app_poi_code": "2828472", "avg_send_time": 2410, "backup_recipient_phone": "[\"13164714130_7645\"]", "caution": " 【如遇缺货】: 缺货时电话与我沟通 收餐人隐私号 13049813276_5307,手机号 139****5027", "city_id": 440300, "ctime": 1555036346, "day_seq": 1, "delivery_time": 0, "detail": "[{\"app_food_code\":\"27262\",\"box_num\":0,\"box_price\":0,\"cart_id\":0,\"food_discount\":1,\"food_name\":\"红管鱿鱼约250g/份\",\"food_property\":\"\",\"price\":23.54,\"quantity\":1,\"sku_id\":\"27262\",\"spec\":\"250g\",\"unit\":\"份\"},{\"app_food_code\":\"24987\",\"box_num\":0,\"box_price\":0,\"cart_id\":0,\"food_discount\":1,\"food_name\":\"带皮猪梅花肉约250g/份\",\"food_property\":\"\",\"price\":15.84,\"quantity\":1,\"sku_id\":\"24987\",\"spec\":\"250g\",\"unit\":\"份\"},{\"app_food_code\":\"27179\",\"box_num\":0,\"box_price\":0,\"cart_id\":0,\"food_discount\":1,\"food_name\":\"[畅销]龙骨约250g/份\",\"food_property\":\"\",\"price\":18.59,\"quantity\":1,\"sku_id\":\"27179\",\"spec\":\"250g\",\"unit\":\"份\"}]", "dinners_number": 0, "expect_deliver_time": 0, "extras": "[{\"act_detail_id\":664795195,\"mt_charge\":0,\"poi_charge\":5,\"reduce_fee\":5,\"remark\":\"满46.0元减5.0元\",\"type\":2},{\"act_detail_id\":665051798,\"mt_charge\":0,\"poi_charge\":4,\"reduce_fee\":4,\"remark\":\"减配送费4.0元\",\"type\":25},{\"act_detail_id\":274839715,\"mt_charge\":0.5,\"poi_charge\":0,\"reduce_fee\":0.5,\"remark\":\"用户使用了支付红包减0.5元\",\"type\":9},{\"mt_charge\":0,\"poi_charge\":0,\"reduce_fee\":0,\"remark\":\"送30元商家代金券\",\"type\":100},{}]", "has_invoiced": 0, "invoice_title": "", "is_favorites": false, "is_poi_first_order": true, "is_pre": 0, "is_third_shipping": 0, "latitude": 22.530194, "logistics_code": "1001", "longitude": 114.08372, "order_id": 28284722536001020, "order_send_time": 1555036356, "original_price": 63.97, "package_bag_money": 0, "pay_type": 2, "pick_type": 0, "poi_receive_detail": "{\"actOrderChargeByMt\":[{\"comment\":\"活动款\",\"feeTypeDesc\":\"活动款\",\"feeTypeId\":10019,\"moneyCent\":50}],\"actOrderChargeByPoi\":[{\"comment\":\"满46.0元减5.0元\",\"feeTypeDesc\":\"活动款\",\"feeTypeId\":10019,\"moneyCent\":500},{\"comment\":\"减配送费4.0元\",\"feeTypeDesc\":\"活动款\",\"feeTypeId\":10019,\"moneyCent\":400}],\"foodShareFeeChargeByPoi\":490,\"logisticsFee\":600,\"onlinePayment\":5447,\"wmPoiReceiveCent\":4406}", "recipient_address": "汇港名苑 (南2区1005)@#广东省深圳市福田区滨河大道滨河大道3119号汇港名苑", "recipient_name": "颜(女士)", "recipient_phone": "13049813276_5307", "remark": "", "result": "ok", "shipper_phone": "", "shipping_fee": 6, "shipping_type": 0, "source_id": 3, "status": 2, "taxpayer_id": "", "total": 54.47, "utime": 1555036346, "wm_order_id_view": 28284722536001020, "wm_poi_address": "深圳市福田区南园街道南华社区滨河路2037号下小庙南区70栋101号滨河街市场", "wm_poi_id": 2828472, "wm_poi_name": "京西菜市(华强南店)", "wm_poi_phone": "13724313878", - } - err := new(PurchaseHandler).OnOrderDetail(result, partner.CreatedPeration) - fmt.Println(err) -} +//func TestOnOrderDetail(t *testing.T) { +// result := map[string]interface{}{ +// "app_order_code": "", "app_poi_code": "2828472", "avg_send_time": 2410, "backup_recipient_phone": "[\"13164714130_7645\"]", "caution": " 【如遇缺货】: 缺货时电话与我沟通 收餐人隐私号 13049813276_5307,手机号 139****5027", "city_id": 440300, "ctime": 1555036346, "day_seq": 1, "delivery_time": 0, "detail": "[{\"app_food_code\":\"27262\",\"box_num\":0,\"box_price\":0,\"cart_id\":0,\"food_discount\":1,\"food_name\":\"红管鱿鱼约250g/份\",\"food_property\":\"\",\"price\":23.54,\"quantity\":1,\"sku_id\":\"27262\",\"spec\":\"250g\",\"unit\":\"份\"},{\"app_food_code\":\"24987\",\"box_num\":0,\"box_price\":0,\"cart_id\":0,\"food_discount\":1,\"food_name\":\"带皮猪梅花肉约250g/份\",\"food_property\":\"\",\"price\":15.84,\"quantity\":1,\"sku_id\":\"24987\",\"spec\":\"250g\",\"unit\":\"份\"},{\"app_food_code\":\"27179\",\"box_num\":0,\"box_price\":0,\"cart_id\":0,\"food_discount\":1,\"food_name\":\"[畅销]龙骨约250g/份\",\"food_property\":\"\",\"price\":18.59,\"quantity\":1,\"sku_id\":\"27179\",\"spec\":\"250g\",\"unit\":\"份\"}]", "dinners_number": 0, "expect_deliver_time": 0, "extras": "[{\"act_detail_id\":664795195,\"mt_charge\":0,\"poi_charge\":5,\"reduce_fee\":5,\"remark\":\"满46.0元减5.0元\",\"type\":2},{\"act_detail_id\":665051798,\"mt_charge\":0,\"poi_charge\":4,\"reduce_fee\":4,\"remark\":\"减配送费4.0元\",\"type\":25},{\"act_detail_id\":274839715,\"mt_charge\":0.5,\"poi_charge\":0,\"reduce_fee\":0.5,\"remark\":\"用户使用了支付红包减0.5元\",\"type\":9},{\"mt_charge\":0,\"poi_charge\":0,\"reduce_fee\":0,\"remark\":\"送30元商家代金券\",\"type\":100},{}]", "has_invoiced": 0, "invoice_title": "", "is_favorites": false, "is_poi_first_order": true, "is_pre": 0, "is_third_shipping": 0, "latitude": 22.530194, "logistics_code": "1001", "longitude": 114.08372, "order_id": 28284722536001020, "order_send_time": 1555036356, "original_price": 63.97, "package_bag_money": 0, "pay_type": 2, "pick_type": 0, "poi_receive_detail": "{\"actOrderChargeByMt\":[{\"comment\":\"活动款\",\"feeTypeDesc\":\"活动款\",\"feeTypeId\":10019,\"moneyCent\":50}],\"actOrderChargeByPoi\":[{\"comment\":\"满46.0元减5.0元\",\"feeTypeDesc\":\"活动款\",\"feeTypeId\":10019,\"moneyCent\":500},{\"comment\":\"减配送费4.0元\",\"feeTypeDesc\":\"活动款\",\"feeTypeId\":10019,\"moneyCent\":400}],\"foodShareFeeChargeByPoi\":490,\"logisticsFee\":600,\"onlinePayment\":5447,\"wmPoiReceiveCent\":4406}", "recipient_address": "汇港名苑 (南2区1005)@#广东省深圳市福田区滨河大道滨河大道3119号汇港名苑", "recipient_name": "颜(女士)", "recipient_phone": "13049813276_5307", "remark": "", "result": "ok", "shipper_phone": "", "shipping_fee": 6, "shipping_type": 0, "source_id": 3, "status": 2, "taxpayer_id": "", "total": 54.47, "utime": 1555036346, "wm_order_id_view": 28284722536001020, "wm_poi_address": "深圳市福田区南园街道南华社区滨河路2037号下小庙南区70栋101号滨河街市场", "wm_poi_id": 2828472, "wm_poi_name": "京西菜市(华强南店)", "wm_poi_phone": "13724313878", +// } +// err := new(PurchaseHandler).OnOrderDetail("", partner.CreatedPeration) +// fmt.Println(err) +//} diff --git a/business/partner/purchase/tiktok_store/mtwm.go b/business/partner/purchase/tiktok_store/mtwm.go index ae73504b4..d6f920b9d 100644 --- a/business/partner/purchase/tiktok_store/mtwm.go +++ b/business/partner/purchase/tiktok_store/mtwm.go @@ -6,8 +6,6 @@ import ( "strings" "sync" - "git.rosy.net.cn/jx-callback/business/model/dao" - "git.rosy.net.cn/baseapi/platformapi/mtwmapi" "git.rosy.net.cn/baseapi/utils" "git.rosy.net.cn/jx-callback/business/jxutils" @@ -31,13 +29,8 @@ type PurchaseHandler struct { locker sync.RWMutex } -func (c *PurchaseHandler) GetOrderStatus(vendorOrgCode, vendorOrderID string) (status int, err error) { - //TODO implement me - panic("implement me") -} - func init() { - if api.MtwmAPI != nil || api.Mtwm2API != nil { + if api.TiktokStore != nil { CurPurchaseHandler = New() partner.RegisterPurchasePlatform(CurPurchaseHandler) } @@ -50,7 +43,7 @@ func New() (obj *PurchaseHandler) { } func (c *PurchaseHandler) GetVendorID() int { - return model.VendorIDMTWM + return model.VendorIDDD } func (p *PurchaseHandler) GetVendorCategories(ctx *jxcontext.Context) (vendorCats []*model.SkuVendorCategory, err error) { @@ -234,17 +227,17 @@ func (p *PurchaseHandler) getUploadImgPoiCode() (poiCode string) { func getAPI(appOrgCode string, storeID int, vendorStoreID string) (apiObj *tiktok_api.API) { apiObj = partner.CurAPIManager.GetAPI(model.VendorIDDD, appOrgCode).(*tiktok_api.API) - if appOrgCode == globals.TiktokShopCode { - var storeDetail *dao.StoreDetail - if storeID != 0 { - storeDetail, _ = dao.GetStoreDetail(dao.GetDB(), storeID, model.VendorIDDD, appOrgCode) - } else if vendorStoreID != "" { - storeDetail, _ = dao.GetStoreDetailByVendorStoreID(dao.GetDB(), vendorStoreID, model.VendorIDDD, appOrgCode) - } - if storeDetail != nil { - apiObj.SetToken(storeDetail.MtwmToken) - } - } + //if appOrgCode == globals.TiktokShopCode { + // var storeDetail *dao.StoreDetail + // if storeID != 0 { + // storeDetail, _ = dao.GetStoreDetail(dao.GetDB(), storeID, model.VendorIDDD, appOrgCode) + // } else if vendorStoreID != "" { + // storeDetail, _ = dao.GetStoreDetailByVendorStoreID(dao.GetDB(), vendorStoreID, model.VendorIDDD, appOrgCode) + // } + // if storeDetail != nil { + // apiObj.SetToken(storeDetail.MtwmToken) + // } + //} return apiObj } diff --git a/business/partner/purchase/tiktok_store/order.go b/business/partner/purchase/tiktok_store/order.go index 1cd44fb75..bbcad868d 100644 --- a/business/partner/purchase/tiktok_store/order.go +++ b/business/partner/purchase/tiktok_store/order.go @@ -5,7 +5,6 @@ import ( "fmt" order_orderDetail_response "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/order_orderDetail/response" tiktokShop "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/tiktok_api" - "git.rosy.net.cn/jx-callback/globals/api" "regexp" "strings" "time" @@ -76,7 +75,7 @@ func (c *PurchaseHandler) Map2Order(orderData map[string]interface{}) (order *mo func (p *PurchaseHandler) getOrder(vendorOrgCode, vendorOrderID, vendorStoreID string) (order *model.GoodsOrder, orderMap *order_orderDetail_response.ShopOrderDetail, err error) { // 平台获取订单详情 - result, err := api.TiktokStore.GetTiktokOrderDetail(vendorOrderID) + result, err := getAPI(vendorOrgCode, 0, vendorStoreID).GetTiktokOrderDetail(vendorOrderID) if err != nil { return nil, nil, err } diff --git a/business/partner/purchase/tiktok_store/order_afs_utils.go b/business/partner/purchase/tiktok_store/order_afs_utils.go index 25a03f081..343beafdd 100644 --- a/business/partner/purchase/tiktok_store/order_afs_utils.go +++ b/business/partner/purchase/tiktok_store/order_afs_utils.go @@ -50,7 +50,7 @@ func (c *PurchaseHandler) OnAfsOrderMsg(msgId, orderId string, msg interface{}) // todo 对于退款与部分退款,order.go与这个文件中对于状态的处理不一致 func (c *PurchaseHandler) onAfsOrderMsg(msgId string, msg interface{}) (retVal *tiktokShop.CallbackResponse) { var err error - orderStatus := c.callbackAfsMsg2Status(msgId, msg) + orderStatus, venderOrgCode := c.callbackAfsMsg2Status(msgId, msg) if orderStatus == nil { return tiktokShop.Err2CallbackResponse(nil, "") } @@ -68,7 +68,7 @@ func (c *PurchaseHandler) onAfsOrderMsg(msgId string, msg interface{}) (retVal * if needCallNew { var afsOrder *model.AfsOrder // 查询售后订单详情 - tiktokAfsOrderDetail, err := api.TiktokStore.QueryAfsOrderDetail(orderStatus.VendorOrderID, false) + tiktokAfsOrderDetail, err := getAPI(utils.Int2Str(venderOrgCode), 0, "").QueryAfsOrderDetail(orderStatus.VendorOrderID, false) if err != nil { globals.SugarLogger.Debug("tic-tok get AfsOrder err :", err) return tiktokShop.Err2CallbackResponse(err, "") @@ -127,7 +127,7 @@ func (c *PurchaseHandler) onAfsOrderMsg(msgId string, msg interface{}) (retVal * return tiktokShop.Err2CallbackResponse(err, "") } -func (c *PurchaseHandler) callbackAfsMsg2Status(msgId string, msg interface{}) (orderStatus *model.OrderStatus) { +func (c *PurchaseHandler) callbackAfsMsg2Status(msgId string, msg interface{}) (orderStatus *model.OrderStatus, vendorOrgCode int) { switch msgId { case tiktokShop.CallbackRefundOrderMsgTagId: // 买家发起售后申请消息 refundOrder := msg.(*tiktokShop.BuyerRefundCreatedData) @@ -151,6 +151,7 @@ func (c *PurchaseHandler) callbackAfsMsg2Status(msgId string, msg interface{}) ( } else { orderMsg.VendorOrderID = orderMsg.RefVendorOrderID } + vendorOrgCode = refundOrder.ShopId case tiktokShop.CallbackUpdateRefundOrderMsgTagId: // 买家修改售后申请消息 refundOrder := msg.(*tiktokShop.BuyerRefundModifiedData) orderMsg := &model.OrderStatus{ @@ -173,6 +174,8 @@ func (c *PurchaseHandler) callbackAfsMsg2Status(msgId string, msg interface{}) ( } else { orderMsg.VendorOrderID = orderMsg.RefVendorOrderID } + vendorOrgCode = refundOrder.ShopId + case tiktokShop.CallbackRefundOrderSuccessMsgTagId: // 退款成功消息 refundOrder := msg.(*tiktokShop.BusinessRefundSuccessData) orderMsg := &model.OrderStatus{ @@ -194,6 +197,8 @@ func (c *PurchaseHandler) callbackAfsMsg2Status(msgId string, msg interface{}) ( } else { orderMsg.VendorOrderID = orderMsg.RefVendorOrderID } + vendorOrgCode = refundOrder.ShopId + case tiktokShop.CallbackRefundOrderRefuseMsgTagId: // 拒绝退款消息 refundOrder := msg.(*tiktokShop.BusinessRefundSuccessData) orderMsg := &model.OrderStatus{ @@ -215,6 +220,8 @@ func (c *PurchaseHandler) callbackAfsMsg2Status(msgId string, msg interface{}) ( } else { orderMsg.VendorOrderID = orderMsg.RefVendorOrderID } + vendorOrgCode = refundOrder.ShopId + case tiktokShop.CallbackRefundShopMsgTagId: // 拒绝退货申请消息 refundOrder := msg.(*tiktokShop.BusinessNotReturnApplyRefusedData) orderMsg := &model.OrderStatus{ @@ -236,6 +243,8 @@ func (c *PurchaseHandler) callbackAfsMsg2Status(msgId string, msg interface{}) ( } else { orderMsg.VendorOrderID = orderMsg.RefVendorOrderID } + vendorOrgCode = refundOrder.ShopId + case tiktokShop.CallbackReturnApplyAgreedMsgTagId: // 同意退货申请消息 refundOrder := msg.(*tiktokShop.BusinessRefundSuccessData) orderMsg := &model.OrderStatus{ @@ -257,6 +266,8 @@ func (c *PurchaseHandler) callbackAfsMsg2Status(msgId string, msg interface{}) ( } else { orderMsg.VendorOrderID = orderMsg.RefVendorOrderID } + vendorOrgCode = refundOrder.ShopId + case tiktokShop.CallbackReturnRefundAgreedMsgTagId: // 同意退款消息 refundOrder := msg.(*tiktokShop.BusinessRefundSuccessData) orderMsg := &model.OrderStatus{ @@ -278,11 +289,13 @@ func (c *PurchaseHandler) callbackAfsMsg2Status(msgId string, msg interface{}) ( } else { orderMsg.VendorOrderID = orderMsg.RefVendorOrderID } + vendorOrgCode = refundOrder.ShopId + default: - return nil + return nil, 0 } - return orderStatus + return orderStatus, vendorOrgCode } func (c *PurchaseHandler) GetAfsStatusFromVendorStatus(resType int, notifyType string) int { diff --git a/business/partner/purchase/tiktok_store/store.go b/business/partner/purchase/tiktok_store/store.go index 072b79781..bafc278ac 100644 --- a/business/partner/purchase/tiktok_store/store.go +++ b/business/partner/purchase/tiktok_store/store.go @@ -1,487 +1,456 @@ package tiktok_store import ( - "encoding/json" "errors" "fmt" - "git.rosy.net.cn/baseapi/platformapi/mtwmapi" + address_create_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/address_create/request" + address_list_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/address_list/request" + address_list_response "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/address_list/response" + freightTemplate_create_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/freightTemplate_create/request" + shop_batchCreateStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_batchCreateStore/request" + shop_bindStoreFreight_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_bindStoreFreight/request" + shop_bindStoreSaleLimit_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_bindStoreSaleLimit/request" + shop_editStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_editStore/request" + shop_getStoreDetail_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_getStoreDetail/request" + shop_storeSuspend_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_storeSuspend/request" + shop_unsuspendStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/shop_unsuspendStore/request" + trade_createTradeLimitTemplate_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/trade_createTradeLimitTemplate/request" + "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/tiktok_api" "git.rosy.net.cn/baseapi/utils" "git.rosy.net.cn/baseapi/utils/errlist" - "git.rosy.net.cn/jx-callback/business/jxcallback/scheduler" "git.rosy.net.cn/jx-callback/business/jxstore/event" "git.rosy.net.cn/jx-callback/business/jxutils" "git.rosy.net.cn/jx-callback/business/jxutils/jxcontext" "git.rosy.net.cn/jx-callback/business/jxutils/tasksch" "git.rosy.net.cn/jx-callback/business/model" "git.rosy.net.cn/jx-callback/business/model/dao" - "git.rosy.net.cn/jx-callback/business/partner" "git.rosy.net.cn/jx-callback/globals" - "git.rosy.net.cn/jx-callback/globals/api" - "math" - "regexp" - "strings" ) -var ( - opTimeErrReg = regexp.MustCompile(`当前配送营业时间为:([\d:~,]*)`) - storeVendorOrgCodeMap = map[string]map[string]string{ - "589": map[string]string{ - "firstTag": mtwmapi.MtwmC4Tag, //经营品类 - "settlementID": "7030017", //结算ID - "poiCert": "1,2,5", //资质列表 - }, - "5873": map[string]string{ - "firstTag": mtwmapi.MtwmSCTag, - "settlementID": "", - "poiCert": "1,2,5,6", - }, - "4123": map[string]string{ - "firstTag": mtwmapi.MtwmSGTag, - "settlementID": "6572945", - "poiCert": "1,5", - }, +func splicingTimeToDoudian(openTime1, closeTime1, openTime2, closeTime2 int16) (timeList string) { + //700 1200 -> 7:00-12:00 + timeStr := "" + if openTime1 != 0 && closeTime1 != 0 { + tOpenTime1 := utils.Int64ToStr(int64(openTime1)) + len1 := len(tOpenTime1) - 2 + s1 := tOpenTime1[:len1] + ":" + tOpenTime1[len1+1:] + tCloseTime1 := utils.Int64ToStr(int64(closeTime1)) + len2 := len(tCloseTime1) - 2 + s2 := tCloseTime1[:len2] + ":" + tCloseTime1[len2+1:] + timeStr += s1 + "-" + s2 + if openTime2 != 0 && closeTime2 != 0 { + tOpenTime2 := utils.Int64ToStr(int64(openTime2)) + len3 := len(tOpenTime2) - 2 + s3 := tOpenTime2[:len3] + ":" + tOpenTime2[len3+1:] + tCloseTime2 := utils.Int64ToStr(int64(closeTime2)) + len4 := len(tCloseTime2) - 2 + s4 := tCloseTime2[:len4] + ":" + tCloseTime2[len4+1:] + timeStr += " " + s3 + "-" + s4 + } } - poiCertMap = map[string]string{ - "1": "门脸图", - "2": "环境图", - "5": "营业执照", - "6": "食品经营许可证", - } -) - -type tEbaiStoreInfo struct { - model.Store - VendorStoreID string `orm:"column(vendor_store_id)"` - RealLastOperator string - EbaiStoreStatus int - SyncStatus int - - ProvinceID int `orm:"column(province_id)"` - CityID int `orm:"column(city_id)"` - DistrictID int `orm:"column(district_id)"` + return timeStr } -func (p *PurchaseHandler) ReadStore(ctx *jxcontext.Context, vendorOrgCode, vendorStoreID, vendorStoreName string) (retVal *dao.StoreDetail, err error) { - result, err := getAPIWithoutToken(vendorOrgCode).PoiGet(vendorStoreID) - if err == nil { - // globals.SugarLogger.Debug(utils.Format4Output(result, false)) - retVal = &dao.StoreDetail{ - Store: model.Store{ - Address: result.Address, - Tel1: result.Phone, - }, - } - retVal.OriginalName = result.Name - _, retVal.Name = jxutils.SplitStoreName(retVal.OriginalName, partner.StoreNameSeparator, globals.StoreNameMtwm) +// shop/batchCreateStore 批量创建门店 +func (P *PurchaseHandler) CreateStore2(db *dao.DaoDB, storeID int, userName string, params map[string]interface{}, storeDetail *dao.StoreDetail) (vendorStoreID string, err error) { + var ( + storeIDs string + lists []shop_batchCreateStore_request.StoreListItem + ShopBatchCreateStoreParam *shop_batchCreateStore_request.ShopBatchCreateStoreParam + ) + timeStr := "" + if storeDetail.OpenTime1 == 0 || storeDetail.CloseTime1 == 0 { + return "", fmt.Errorf("营业时间必填") + } else { + timeStr = splicingTimeToDoudian(storeDetail.OpenTime1, storeDetail.CloseTime1, storeDetail.OpenTime2, storeDetail.CloseTime2) + } + m := make(map[int64]string) + for j := 1; j <= 7; j++ { + m[int64(j)] = timeStr + } + list := shop_batchCreateStore_request.StoreListItem{ + RowId: 1, + Name: storeDetail.Name, + StoreCode: storeDetail.VendorStoreID, + Longitude: utils.Float64ToStr(jxutils.IntCoordinate2Standard(storeDetail.Lng)), + Latitude: utils.Float64ToStr(jxutils.IntCoordinate2Standard(storeDetail.Lat)), + Province: storeDetail.ProvinceName, + City: storeDetail.CityName, + District: storeDetail.DistrictName, + Address: storeDetail.Address, + Contact: storeDetail.Tel1, + OpenTime: &shop_batchCreateStore_request.OpenTime{ + DayMap: m, + }, + } + lists = append(lists, list) + ShopBatchCreateStoreParam = &shop_batchCreateStore_request.ShopBatchCreateStoreParam{ + StoreList: lists, + } - retVal.SetOpTime(openTimeMtwm2JX(result.ShippingTime)) - retVal.Status = bizStatusMtwm2JX(result.OpenLevel, result.IsOnline) - - tel2 := result.StandbyTel - if tel2 != "" && tel2 != retVal.Tel1 { - retVal.Tel2 = tel2 - } - - retVal.Lng = int(result.Longitude) - retVal.Lat = int(result.Latitude) - - lng := jxutils.IntCoordinate2Standard(retVal.Lng) - lat := jxutils.IntCoordinate2Standard(retVal.Lat) - db := dao.GetDB() - retVal.DistrictCode = api.AutonaviAPI.GetCoordinateDistrictCode(lng, lat) - city, err := dao.GetPlaceByCode(db, result.CityID) - retVal.CityName = city.Name - retVal.CityCode = result.CityID - - poiCode := result.AppPoiCode - retVal.VendorStoreID = vendorStoreID - retVal.ID = int(utils.Str2Int64WithDefault(poiCode, 0)) - retVal.DeliveryRangeType = model.DeliveryRangeTypePolygon - var deliveryRangeInfo []map[string]interface{} - deliveryRangeInfo, err = getAPIWithoutToken(vendorOrgCode).ShippingFetch(poiCode) - if err != nil { - deliveryRangeInfo, err = getAPIWithoutToken(vendorOrgCode).ShippingList(poiCode) - } - if err == nil { - if len(deliveryRangeInfo) > 0 { - retVal.DeliveryRange = rangeMtwm2JX(deliveryRangeInfo[0]["area"].(string)) - logisticsCode := utils.Interface2String(deliveryRangeInfo[0]["logistics_code"]) - if logisticsCode == "" || logisticsCode == mtwmapi.PeiSongTypeSelf { - retVal.DeliveryType = scheduler.StoreDeliveryTypeByStore - } else { - retVal.DeliveryType = scheduler.StoreDeliveryTypeByPlatform - } + if resp, err := getAPI("", storeID, storeDetail.VendorStoreID).BatchCreateStore(ShopBatchCreateStoreParam); err != nil { + return "", err + } else { + for k, v := range resp.ResultList { + if k != len(resp.ResultList) { + storeIDs += utils.Int64ToStr(v.Store.StoreId) + "," } + storeIDs += utils.Int64ToStr(v.Store.StoreId) } - return retVal, nil + return storeIDs, nil } - return nil, err -} -func (p *PurchaseHandler) CreateStore(db *dao.DaoDB, storeID int, userName string) (err error) { - return p.UpdateStore(db, storeID, userName) } -func (p *PurchaseHandler) CreateStore2(db *dao.DaoDB, storeID int, userName string, params map[string]interface{}, storeDetail *dao.StoreDetail) (vendorStoreID string, err error) { - vendorOrgCode := params["vendorOrgCode"].(string) - if vendorOrgCode == "" { - return "", fmt.Errorf("平台账号必传!") - } - cityName := storeDetail.CityName - if strings.Contains(cityName, "市") { - cityName = strings.Replace(cityName, "市", "", strings.LastIndex(cityName, "市")) - } - shippingTime := "" - if storeDetail.OpenTime1 != 0 && storeDetail.CloseTime1 != 0 { - shippingTime += jxutils.JxOperationTime2StrTime(storeDetail.OpenTime1) - shippingTime += "-" - shippingTime += jxutils.JxOperationTime2StrTime(storeDetail.CloseTime1) - if storeDetail.OpenTime2 != 0 && storeDetail.CloseTime2 != 0 { - shippingTime += "," - shippingTime += jxutils.JxOperationTime2StrTime(storeDetail.OpenTime2) - shippingTime += "-" - shippingTime += jxutils.JxOperationTime2StrTime(storeDetail.CloseTime2) - } - } - vendorInfoMap := storeVendorOrgCodeMap[vendorOrgCode] - poiSettleSaveParam := &mtwmapi.PoiSettleSaveParam{ - Type: 1, //创建 - ApplyInfos: []*mtwmapi.ApplyInfo{ - &mtwmapi.ApplyInfo{ - AppPoiCode: utils.Int2Str(storeDetail.ID), - SettlementID: utils.Str2Int(vendorInfoMap["settlementID"]), //结算ID,暂时还没得 - MultiPoiBasicInfo: &mtwmapi.MultiPoiBasicInfo{ - Name: params["vendorStoreName"].(string), - City: cityName, - Address: storeDetail.Address, - Longitude: utils.Float64ToStr(jxutils.IntCoordinate2Standard(storeDetail.Lng)), - Latitude: utils.Float64ToStr(jxutils.IntCoordinate2Standard(storeDetail.Lat)), - FirstTag: vendorInfoMap["firstTag"], - CallCenter: storeDetail.Tel1, - ContactPhone: storeDetail.Tel1, - ContactName: storeDetail.IDName, - EcommerceAccountPhone: "18048531223", //石总的手机 - ShippingTime: shippingTime, - }, - MultiPoiShippingInfo: &mtwmapi.MultiPoiShippingInfo{ - ShippingType: 5, //1:商家自配 5:美团专送,101:美团快送 - //美团专送不需要输下面这俩 - // MinPrice: params["minPrice"].(float64), - // ShippingFee: params["shippingFee"].(float64), - }, - //资质 - }, - }, - } - switchCertType := func(certType string) (licensePic, licenseSocialCreditCode, licenseNumber, licenseLegalPerson, licenseAddress, licenseValidStartDate, licenseValidity string, isLongTime int) { - switch certType { - case "1": - licensePic = storeDetail.StoreFrontPic - case "2": - licensePic = storeDetail.StoreInPic - case "5": - licensePic = storeDetail.Licence - licenseSocialCreditCode = storeDetail.LicenceCode - licenseNumber = storeDetail.LicenceCode - licenseLegalPerson = storeDetail.LicenceOwnerName - licenseAddress = storeDetail.LicenceAddress - licenseValidStartDate = storeDetail.LicenceValid - if storeDetail.LicenceExpire == "" { - isLongTime = 1 - } else { - licenseValidity = storeDetail.LicenceExpire - } - case "6": - licensePic = storeDetail.Licence2Image - licenseSocialCreditCode = storeDetail.Licence2Code - licenseNumber = storeDetail.Licence2Code - licenseLegalPerson = storeDetail.LicenceOwnerName - licenseAddress = storeDetail.LicenceAddress - licenseValidStartDate = storeDetail.Licence2Valid - if storeDetail.Licence2Expire == "" { - isLongTime = 1 - } else { - licenseValidity = storeDetail.Licence2Expire - } - } - return licensePic, licenseSocialCreditCode, licenseNumber, licenseLegalPerson, licenseAddress, licenseValidStartDate, licenseValidity, isLongTime - } - var certs []*mtwmapi.MultiPoiCertInfo - for _, v := range strings.Split(vendorInfoMap["poiCert"], ",") { - cert := &mtwmapi.MultiPoiCertInfo{ - Type: utils.Str2Int(v), - LicenseName: poiCertMap[v], - } - cert.LicensePic, cert.LicenseSocialCreditCode, cert.LicenseNumber, cert.LicenseLegalPerson, cert.LicenseAddress, cert.LicenseValidStartDate, cert.LicenseValidity, cert.IsLongTime = switchCertType(v) - certs = append(certs, cert) - } - poiSettleSaveParam.ApplyInfos[0].MultiPoiCertInfos = certs - mtapi := getAPIWithoutToken(vendorOrgCode) - if vendorStoreID, err = mtapi.PoiSettleSave(poiSettleSaveParam); err == nil { - err = mtapi.PoiSettleAuditSubmit([]string{vendorStoreID}) - } - return vendorStoreID, err -} - -func (p *PurchaseHandler) DeleteStore(db *dao.DaoDB, storeID int, userName string) (err error) { - return err -} - -func (p *PurchaseHandler) UpdateStore(db *dao.DaoDB, storeID int, userName string) (err error) { - var name string +// shop/editStore 编辑门店信息 正向推送平台 +func (P *PurchaseHandler) UpdateStore(db *dao.DaoDB, storeID int, userName string) (err error) { + globals.SugarLogger.Debugf("doudian Update storeID:%d, userName:%s", storeID, userName) + var ( + storeInfo *dao.StoreDetail + name string + ) if db == nil { db = dao.GetDB() } - mtapi := getAPI(getStoreVendorOrgCode(storeID), storeID, "") - storeDetail, err := dao.GetStoreDetail(db, storeID, model.VendorIDMTWM, "") + sqlStr := ` SELECT + t1.*, + t2.status, t2.vendor_store_id, t2.vendor_org_code, + IF(t1.updated_at > t2.updated_at, t1.last_operator, t2.last_operator) real_last_operator, t2.sync_status, t2.vendor_store_name + FROM store t1 + LEFT JOIN store_map t2 ON t1.id = t2.store_id AND t2.vendor_id = ? AND (t2.deleted_at = ?) + WHERE t1.id = ? + ORDER BY t2.updated_at` + err = dao.GetRow(db, &storeInfo, sqlStr, model.VendorIDDD, utils.DefaultTimeValue, utils.Int2Str(storeID)) if err != nil { return err } errList := errlist.New() + timeStr := "" + m := make(map[int64]string) + if storeInfo.OpenTime1 != 0 && storeInfo.CloseTime1 != 0 { + timeStr = splicingTimeToDoudian(storeInfo.OpenTime1, storeInfo.CloseTime1, storeInfo.OpenTime2, storeInfo.CloseTime2) + for j := 1; j <= 7; j++ { + m[int64(j)] = timeStr + } + } + vendorStoreID := &shop_getStoreDetail_request.ShopGetStoreDetailParam{ + StoreId: utils.Str2Int64(storeInfo.VendorStoreID), + } - remoteStoreInfo, err := mtapi.PoiGet(storeDetail.VendorStoreID) + api := getAPI(storeInfo.VendorOrgCode, storeID, utils.Int64ToStr(vendorStoreID.StoreId)) + if globals.EnableDdStoreWrite { + remoteStoreInfo, err2 := api.GetStoreDetail(vendorStoreID) + if err2 != nil { + return err2 + } + if remoteStoreInfo.StoreDetail.Store.StoreId == 0 { + return fmt.Errorf("ID:%d 的门店不存在,请先创建", utils.Str2Int64(storeInfo.VendorStoreID)) + } + mergedStoreStatus := jxutils.MergeStoreStatus(storeInfo.Status, storeInfo.VendorStatus) + name = remoteStoreInfo.StoreDetail.Store.Name + if storeInfo.SyncStatus&(model.SyncFlagNewMask|model.SyncFlagStoreName) != 0 { + if storeInfo.VendorStoreName != "" { + name = storeInfo.VendorStoreName + } + } + store := fmt.Sprintf("门店id:%d,门店名称:%s,第三方门店状态:%d,本地修改前门店状态%d,本地门店修改后状态:%d,第三方平台Id(抖店):%s", storeID, remoteStoreInfo.StoreDetail.Store.Name, remoteStoreInfo.StoreDetail.Store.State, storeInfo.Status, mergedStoreStatus, storeInfo.VendorOrgCode) + event.AddOperateEvent(jxcontext.AdminCtx, jxcontext.AdminCtx.GetTrackInfo(), store, "", "", 10, "UpdateStore") + params := &shop_editStore_request.ShopEditStoreParam{ + StoreId: remoteStoreInfo.StoreDetail.Store.StoreId, //平台id不可修改 + Name: name, + StoreCode: utils.Int2Str(storeInfo.ID), //自用编码即很本地storeID + Latitude: utils.Int2Str(storeInfo.Lat), + Longitude: utils.Int2Str(storeInfo.Lng), + Province: storeInfo.ProvinceName, + City: storeInfo.CityName, + District: storeInfo.DistrictName, + Address: storeInfo.Address, + Contact: storeInfo.Tel1, + OpenTime: &shop_editStore_request.OpenTime{ + DayMap: m, + }, + } + //修改店铺状态 + if storeInfo.SyncStatus&(model.SyncFlagNewMask|model.SyncFlagStoreStatus) != 0 { + errList.AddErr(P.UpdateStoreStatus(jxcontext.AdminCtx, storeInfo.VendorOrgCode, storeID, storeInfo.VendorStoreID, mergedStoreStatus)) + } + _, err3 := api.EditStore(params) + if err3 != nil { + errList.AddErr(err3) + } + } + return err +} + +// UpdateStoreStatus shop/unsuspendStore 门店恢复营业 +func (p *PurchaseHandler) UpdateStoreStatus(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, status int) (err error) { + isOnline := bizStatusJX2DouDian(status) + api := getAPI(vendorOrgCode, storeID, vendorStoreID) + if globals.EnableDdStoreWrite { + if isOnline != tiktok_api.StoreStatusOnline { //暂停营业状态 + unsuspendStoreID := &shop_unsuspendStore_request.ShopUnsuspendStoreParam{ + StoreId: utils.Str2Int64(vendorStoreID), + } + _, err = api.UnsuspendStore(unsuspendStoreID) + } else { //恢复营业 + suspendStoreID := &shop_storeSuspend_request.ShopStoreSuspendParam{ + StoreId: utils.Str2Int64(vendorStoreID), + } + getStoreID := &shop_getStoreDetail_request.ShopGetStoreDetailParam{ + StoreId: utils.Str2Int64(vendorStoreID), + } + //平台上店铺状态 + remoteStoreInfo, err2 := api.GetStoreDetail(getStoreID) + if err2 != nil { + return err2 + } + if remoteStoreInfo.StoreDetail.Store.SuspendType == tiktok_api.SuspendTypePlatformPenalty { + err = errors.New("门店因平台处罚暂停营业,不可主动修改营业状态") + } else { + _, err = api.StoreSuspend(suspendStoreID) + } + } + } + return err +} + +// /freightTemplate/create 创建运费模板 +func (P *PurchaseHandler) CreateFreightTemplate(templateInfo freightTemplate_create_request.FreightTemplateCreateParam, storeID, vendorStoreID int64) error { + var ( + db *dao.DaoDB + ) + if templateInfo.Template.RuleType > 0 { + templateInfo.Template.CalculateType = tiktok_api.CalculateTypeNum + } + info := &freightTemplate_create_request.FreightTemplateCreateParam{ + Template: templateInfo.Template, + Columns: templateInfo.Columns, + } + api := getAPI("", int(storeID), utils.Int64ToStr(vendorStoreID)) + + resp, err := api.FreightTemplateCreate(info) if err != nil { return err } - mergedStoreStatus := jxutils.MergeStoreStatus(storeDetail.Status, storeDetail.VendorStatus) - name = remoteStoreInfo.Name - if storeDetail.SyncStatus&(model.SyncFlagNewMask|model.SyncFlagStoreName) != 0 { - if storeDetail.VendorStoreName != "" { - name = storeDetail.VendorStoreName - } - // else { - // name = jxutils.ComposeStoreName(storeDetail.Store.Name, model.VendorIDMTWM) - // } + //创建成功后进行绑定 + bindInfo := &shop_bindStoreFreight_request.ShopBindStoreFreightParam{ + StoreId: vendorStoreID, + FreightId: resp.TemplateId, } - store := fmt.Sprintf("门店id:%d,门店名称:%s,第三方门店状态:%d,本地修改前门店状态%d,本地门店修改后状态:%d,第三方平台Id(美团):%s", storeID, remoteStoreInfo.Name, remoteStoreInfo.IsOnline, storeDetail.Status, mergedStoreStatus, storeDetail.VendorOrgCode) - event.AddOperateEvent(jxcontext.AdminCtx, jxcontext.AdminCtx.GetTrackInfo(), store, "", "", 10, "UpdateStore") - // openLevel, isOnline := bizStatusJX2Mtwm(mergedStoreStatus) - //TODO 美团暂时不用那个电话 - phone := storeDetail.Tel1 - // if storeDetail.MarketManPhone != "" { - // phone = storeDetail.MarketManPhone - // } else { - // phone = model.VendorStoreTel - // } - params := map[string]interface{}{ - "name": name, //jxutils.ComposeStoreName(storeDetail.Store.Name, model.VendorIDMTWM), - "address": storeDetail.Address, // 美团好像地址也不能改的? - "longitude": jxutils.IntCoordinate2Standard(int(remoteStoreInfo.Longitude)), - "latitude": jxutils.IntCoordinate2Standard(int(remoteStoreInfo.Latitude)), - "phone": phone, - "shipping_fee": remoteStoreInfo.ShippingFee, - "shipping_time": remoteStoreInfo.ShippingTime, - "open_level": remoteStoreInfo.OpenLevel, - "is_online": remoteStoreInfo.IsOnline, - "third_tag_name": remoteStoreInfo.ThirdTagName, - "promotion_info": storeDetail.PromoteInfo, + _, err1 := api.BindFreightTemplate(bindInfo) + if err != nil { + return err1 } - // globals.SugarLogger.Debug(utils.Format4Output(params, false)) - if globals.EnableMtwmStoreWrite { - errList.AddErr(mtapi.PoiSave(storeDetail.VendorStoreID, params)) + //并写入数据库 + freightInfo := model.FreightTemplate{ + StoreID: storeID, + VendorStoreID: vendorStoreID, + TemplateID: resp.TemplateId, } - // PoiSave有时会报错:商家已接入美团配送,不可修改门店配送相关信息,这里放弃信息修改 - // if err != nil { - // if utils.IsErrMatch(err, utils.Int2Str(mtwmapi.ErrCodeCanNotModifyStoreDeliveryInfo), nil) { - // globals.SugarLogger.Infof("mtwm UpdateStore vendorStoreID:%s, params:%s failed with err:%v", storeDetail.VendorStoreID, utils.Format4Output(params, true), err) - // if storeDetail.SyncStatus&(model.SyncFlagNewMask|model.SyncFlagStoreStatus) != 0 { - // err = p.UpdateStoreStatus(jxcontext.AdminCtx, storeDetail.VendorOrgCode, storeID, storeDetail.VendorStoreID, mergedStoreStatus) - // } else { - // err = nil - // } - // } - // errList.AddErr(err) - // } - if storeDetail.SyncStatus&(model.SyncFlagNewMask|model.SyncFlagStoreStatus) != 0 { - errList.AddErr(p.UpdateStoreStatus(jxcontext.AdminCtx, storeDetail.VendorOrgCode, storeID, storeDetail.VendorStoreID, mergedStoreStatus)) - } - errList.AddErr(p.UpdateStoreOpTime(jxcontext.AdminCtx, storeDetail.VendorOrgCode, storeID, storeDetail.VendorStoreID, storeDetail.GetOpTimeList())) - // errList.AddErr(p.UpdateStoreBoxFee(jxcontext.AdminCtx, storeDetail.VendorOrgCode, storeID, storeDetail.VendorStoreID)) - return errList.GetErrListAsOne() -} - -func (p *PurchaseHandler) RefreshAllStoresID(ctx *jxcontext.Context, parentTask tasksch.ITask, isAsync bool) (hint string, err error) { - return "", errors.New("美团外卖不支持此操作") -} - -func (p *PurchaseHandler) onStoreStatusChanged(msg *mtwmapi.CallbackMsg) (response *mtwmapi.CallbackResponse) { - var err error - vendorStoreID := msg.FormData.Get("app_poi_code") - storeStatus := 0 - if msg.Cmd == mtwmapi.MsgTypeStoreStatusChanged { - poiStatus := int(utils.Str2Int64(msg.FormData.Get("poi_status"))) - if poiStatus == mtwmapi.MsgPoiStatusOpened { - storeStatus = model.StoreStatusOpened - } else if poiStatus == mtwmapi.MsgPoiStatusClosed { - storeStatus = model.StoreStatusClosed - } else if poiStatus == mtwmapi.MsgPoiStatusOffline { - storeStatus = model.StoreStatusDisabled - } else { - storeStatus, err = p.GetStoreStatus(jxcontext.AdminCtx, "", 0, vendorStoreID) - } - } else if msg.Cmd == mtwmapi.MsgTypeStoreAuditStatusChanged { - auditDetails := []map[string]interface{}{} - auditDetail := msg.FormData.Get("audit_detail") - openFlag := false - openCount := 0 - closeFlag := false - if err = json.Unmarshal([]byte(auditDetail), &auditDetails); err == nil { - for _, v := range auditDetails { - if v["module_status"].(string) == "3" || v["module_status"].(string) == "5" || v["module_status"].(string) == "7" { - closeFlag = true - break - } - if v["module_status"].(string) == "6" { - openCount++ - } - } - if openCount == len(auditDetails) { - openFlag = true - } - if closeFlag { - storeStatus = model.StoreStatusDisabled - } else if openFlag { - storeStatus = model.StoreStatusOpened - } else { - storeStatus = model.StoreStatusClosed - } - } - } - - if err == nil { - err = partner.CurStoreManager.OnStoreStatusChanged(vendorStoreID, model.VendorIDMTWM, storeStatus) - } - response = mtwmapi.Err2CallbackResponse(err, "") - // 操作日志(美团外卖) - ctx := jxcontext.AdminCtx - store := fmt.Sprintf("美团外卖回调门店改变回调(营业状态/审核状态):门店id:%s,美团门店状态:%d.[121营业,120休息,18上线,19下线],本地修改后状态[%d]", vendorStoreID, int(utils.Str2Int64(msg.FormData.Get("poi_status"))), storeStatus) - event.AddOperateEvent(ctx, ctx.GetTrackInfo(), store, "", "", 10, "UpdateStore") - return response -} - -func (p *PurchaseHandler) GetStoreStatus(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string) (storeStatus int, err error) { - result, err := getAPI(vendorOrgCode, storeID, "").PoiGet(vendorStoreID) - if err == nil { - return bizStatusMtwm2JX(result.OpenLevel, result.IsOnline), nil - } - return 0, err -} - -func (p *PurchaseHandler) EnableAutoAcceptOrder(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, isSetEnable bool) (err error) { - return err -} - -func (c *PurchaseHandler) UpdateStoreStatus(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, status int) (err error) { - openLevel, isOnline := bizStatusJX2Mtwm(status) - if globals.EnableMtwmStoreWrite { - if isOnline != mtwmapi.PoiStatusOnline { - err = getAPI(vendorOrgCode, storeID, vendorStoreID).PoiOffline(vendorStoreID) - } else { - if err = getAPI(vendorOrgCode, storeID, vendorStoreID).PoiOnline(vendorStoreID); err == nil { // 这个函数成功返回也并不表示上线成功。。。 - remoteStoreInfo, err2 := getAPI(vendorOrgCode, storeID, vendorStoreID).PoiGet(vendorStoreID) - if err = err2; err != nil { - return err - } - if remoteStoreInfo.IsOnline == mtwmapi.PoiStatusOnline { - if openLevel == mtwmapi.PoiOpenLevelHaveRest { - err = getAPI(vendorOrgCode, storeID, vendorStoreID).PoiClose(vendorStoreID) - } else { - err = getAPI(vendorOrgCode, storeID, vendorStoreID).PoiOpen(vendorStoreID) - } - } else { - err = errors.New("门店还未上线,不能修改营业状态") - } - store := fmt.Sprintf("美团外卖回调门店改变回调(营业状态/审核状态):门店id:%s,美团门店状态:%d.[121营业,120休息,18上线,19下线],本地修改后状态[%d]", vendorStoreID, remoteStoreInfo.OpenLevel, openLevel) - event.AddOperateEvent(ctx, ctx.GetTrackInfo(), store, "", "", 10, "UpdateStore") - } - } - } - return err -} - -func errOpStr2Int16(str string) []int16 { - list := strings.Split(str, "~") - if len(list) >= 2 { - return []int16{jxutils.StrTime2JxOperationTime(list[0]+":00", 0), jxutils.StrTime2JxOperationTime(list[1]+":00", 2359)} + if err = dao.CreateEntity(db, freightInfo); err != nil { + return err } return nil } -func getOpTimeListFromErr(err error) (opTimeList []int16) { - if errExt, ok := err.(*utils.ErrorWithCode); ok && errExt.IntCode() == mtwmapi.ErrCodeOpFailed { - if result := opTimeErrReg.FindStringSubmatch(errExt.ErrMsg()); len(result) >= 2 { - timeStrList := strings.Split(result[1], ",") - for _, v := range timeStrList { - v = utils.TrimBlankChar(v) - if len(v) == len("00:00~02:00") { - opTimeList = append(opTimeList, errOpStr2Int16(v)...) - } - } - } +// /shop/bindStoreFreight 门店绑定运费模版 +//门店绑定运费模版,运费模版必须属于门店关联的抖店,且门店与运费模版是一对一关系 +func (P *PurchaseHandler) ShopBindStoreFreight(storeID, freightID int64) error { + param := &shop_bindStoreFreight_request.ShopBindStoreFreightParam{ + StoreId: storeID, + FreightId: freightID, } - return opTimeList + api := getAPI("", int(storeID), "") + _, err := api.BindFreightTemplate(param) + if err != nil { + return err + } + return nil } -// 此函数只是简单实现,不支持区间切分,只做单一区间限制 -func constrainOpTimeList(opTimeList, validOpTimeList []int16) (newOpTimeList []int16) { - for k := 0; k < len(opTimeList); k += 2 { - beginTime := opTimeList[k] - endTime := opTimeList[k+1] - for k2 := 0; k2 < len(validOpTimeList); k2 += 2 { - beginTime2 := validOpTimeList[k2] - endTime2 := validOpTimeList[k2+1] - if beginTime >= beginTime2 && beginTime <= endTime2 { - newOpTimeList = append(newOpTimeList, beginTime) - newOpTimeList = append(newOpTimeList, int16(math.Min(float64(endTime), float64(endTime2)))) - } else if beginTime2 >= beginTime && beginTime2 <= endTime { - newOpTimeList = append(newOpTimeList, beginTime2) - newOpTimeList = append(newOpTimeList, int16(math.Min(float64(endTime), float64(endTime2)))) - } - } +// /address/create 创建店铺地址库(新建即绑定) +func (P *PurchaseHandler) CreateAddress(addressInfo address_create_request.AddressCreateParam) (addressID int64, err error) { + info := &address_create_request.AddressCreateParam{ + Address: addressInfo.Address, + StoreId: addressInfo.StoreId, } - return newOpTimeList + api := getAPI("", 0, utils.Int64ToStr(info.StoreId)) + resp, err := api.AddressCreate(info) + if err != nil { + return 0, err + } + //添加进数据库page_shop + //获取门店信息 + //storeID := &shop_getStoreDetail_request.ShopGetStoreDetailParam{ + // StoreId: addressInfo.StoreId, + //} + //storeInfo, err1 := api.DouDianApi.GetStoreDetail(storeID) + //if err1 != nil { + // return 0, err1 + //} + //createAddress := &model.PageShop{ //此表暂存门店售后地址库 + // Name: storeInfo.StoreDetail.Store.Name, + // VendorID: model.VendorIDDouDian, + // VendorStoreID: utils.Int64ToStr(storeInfo.StoreDetail.Store.StoreId), //抖店平台ID + // OrgCode: storeInfo.StoreDetail.Store.StoreCode, //暂时用来存放京西平台门店ID + // VendorStatus: utils.Int64ToStr(storeInfo.StoreDetail.Store.State), + // Status: 0, + // CityCode: utils.Str2Int(storeInfo.StoreDetail.Store.CityCode), + // DistrictCode: utils.Str2Int(storeInfo.StoreDetail.Store.DistrictCode), + // Address: storeInfo.StoreDetail.Store.Address, + // Lng: utils.Str2Float64(storeInfo.StoreDetail.Store.Longitude), + // Lat: utils.Str2Float64(storeInfo.StoreDetail.Store.Latitude), + // Tel1: storeInfo.StoreDetail.Store.Contact, + //} + //if err = dao.CreateEntity(dao.GetDB(), createAddress); err != nil { + // return 0, err + //} + return resp.AddressId, nil } -func (c *PurchaseHandler) UpdateStoreOpTime(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, opTimeList []int16) (err error) { - shippingTime := openTimeJX2Mtwm(opTimeList) - if globals.EnableMtwmStoreWrite { - err = getAPI(vendorOrgCode, storeID, vendorStoreID).PoiShipTimeUpdate(vendorStoreID, shippingTime) - if err != nil { - shippingTime = "" - if validOpTimeList := getOpTimeListFromErr(err); len(validOpTimeList) > 0 { - shippingTime = openTimeJX2Mtwm(constrainOpTimeList(opTimeList, validOpTimeList)) - } - if shippingTime != "" { - err = getAPI(vendorOrgCode, storeID, vendorStoreID).PoiShipTimeUpdate(vendorStoreID, shippingTime) - } - } +// /address/list 获取售后地址列表接口 +//分页获取商家地址列表 +func (P *PurchaseHandler) GetAddressList(param *address_list_request.AddressListParam) (*address_list_response.AddressListData, error) { + //不传入ID则是获取所有门店售后地址列表 + info := &address_list_request.AddressListParam{ + PageSize: 10, + PageNo: 1, + OrderBy: param.OrderBy, + OrderField: param.OrderField, + } + if param.StoreId != 0 { + info.StoreId = param.StoreId + } + listInfo, err := getAPI("", 0, utils.Int64ToStr(info.StoreId)).GetAddressList(info) + if err != nil { + return nil, err + } + return listInfo, nil +} + +// /trade/createTradeLimitTemplate 创建限售模板 +func (P *PurchaseHandler) CreateTradeLimitTemplate(template trade_createTradeLimitTemplate_request.TradeCreateTradeLimitTemplateParam) (tradeLimitID int64, err error) { + info := &trade_createTradeLimitTemplate_request.TradeCreateTradeLimitTemplateParam{ + StoreId: template.StoreId, + TradeLimitRuleRequestList: template.TradeLimitRuleRequestList, + } + resp, err := getAPI("", 0, utils.Int64ToStr(info.StoreId)).CreateTradeLimitTemplate(info) + if err != nil { + return 0, err + } + return resp.TradeLimitId, nil +} + +// /shop/bindStoreSaleLimit 门店绑定限售模板 +func (P *PurchaseHandler) BindStoreSaleLimit(storeID, saleLimitTemplateID int64) error { + info := &shop_bindStoreSaleLimit_request.ShopBindStoreSaleLimitParam{ + StoreId: storeID, + SaleLimitId: saleLimitTemplateID, + } + if _, err := getAPI("", 0, utils.Int64ToStr(info.StoreId)).BindStoreSaleLimit(info); err != nil { + return err + } + return nil +} + +func (P *PurchaseHandler) UpdateStoreOpTime(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, opTimeList []int16) (err error) { + t1 := opTimeList[0] + t2 := opTimeList[1] + t3 := opTimeList[2] + t4 := opTimeList[4] + timeStr := splicingTimeToDoudian(t1, t2, t3, t4) + m := make(map[int64]string) + for j := 1; j <= 7; j++ { + m[int64(j)] = timeStr + } + params := &shop_editStore_request.ShopEditStoreParam{ + StoreId: utils.Str2Int64(vendorStoreID), + OpenTime: &shop_editStore_request.OpenTime{ + DayMap: m, + }, + } + if globals.EnableDdStoreWrite { + _, err = getAPI(vendorOrgCode, storeID, vendorStoreID).EditStore(params) } return err } -func (c *PurchaseHandler) GetAllStoresVendorID(ctx *jxcontext.Context, vendorOrgCode string) (vendorStoreIDs []string, err error) { - vendorStoreIDs, err = getAPIWithoutToken(vendorOrgCode).PoiGetIDs() - return vendorStoreIDs, err -} - -func (c *PurchaseHandler) UpdateStoreCustomID(ctx *jxcontext.Context, vendorOrgCode, vendorStoreID string, storeID int64) (err error) { - return err -} - -func (c *PurchaseHandler) UpdateStoreBoxFee(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string) (err error) { - boxFee, err := dao.GetSysConfigAsInt64(dao.GetDB(), model.ConfigSysMtwmBoxFee) - if err == nil { - if globals.EnableMtwmStoreWrite && globals.IsProductEnv() { - err = getAPI(vendorOrgCode, storeID, vendorStoreID).PackagePriceUpdate(vendorStoreID, 1, int(boxFee)) - } +func (P *PurchaseHandler) GetStoreStatus(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string) (storeStatus int, err error) { + params := &shop_getStoreDetail_request.ShopGetStoreDetailParam{ + StoreId: utils.Str2Int64(vendorStoreID), } + result, err := getAPI(vendorOrgCode, storeID, vendorStoreID).GetStoreDetail(params) + if err != nil { + return 0, err + } + status := bizStatusJX2DouDian(int(result.StoreDetail.Store.State)) + return status, nil +} + +func (P *PurchaseHandler) EnableAutoAcceptOrder(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, isSetEnable bool) (err error) { return err } -func (c *PurchaseHandler) UpdateStoreLineStatus(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, lineStatus int) (err error) { +// 获取店铺所有平台ID +func (P *PurchaseHandler) GetAllStoresVendorID(ctx *jxcontext.Context, vendorOrgCode string) (vendorStoreIDs []string, err error) { + //param := &shop_getStoreList_request.ShopGetStoreListParam{ + // Page: 0, + // PageSize: 10, + //} + //storeList, err := api.DouDianApi.GetStoreList(param) + //if err != nil { + // return nil, err + //} + //if len(storeList.StoreDetailList) > 0 { + // vendorStoreIDs = make([]string, len(storeList.StoreDetailList)) + // for k, v := range storeList.StoreDetailList { + // vendorStoreIDs[k] = utils.Int64ToStr(v.Store.StoreId) + // } + //} + //return vendorStoreIDs, err + return nil, err +} + +func (P *PurchaseHandler) UpdateStoreLineStatus(ctx *jxcontext.Context, vendorOrgCode string, storeID int, vendorStoreID string, lineStatus int) (err error) { + api := getAPI(vendorOrgCode, storeID, vendorStoreID) if lineStatus == model.StoreStatusOpened { - err = getAPI(vendorOrgCode, storeID, vendorStoreID).PoiOnline(vendorStoreID) + param := &shop_storeSuspend_request.ShopStoreSuspendParam{ + StoreId: utils.Str2Int64(vendorStoreID), + } + _, err = api.StoreSuspend(param) } else { - err = getAPI(vendorOrgCode, storeID, vendorStoreID).PoiOffline(vendorStoreID) + param := &shop_unsuspendStore_request.ShopUnsuspendStoreParam{ + StoreId: utils.Str2Int64(vendorStoreID), + } + _, err = api.UnsuspendStore(param) } return err } +func (P *PurchaseHandler) ReadStore(ctx *jxcontext.Context, vendorOrgCode, vendorStoreID, vendorStoreName string) (store *dao.StoreDetail, err error) { + return nil, err +} + +func (P *PurchaseHandler) RefreshAllStoresID(ctx *jxcontext.Context, parentTask tasksch.ITask, isAsync bool) (hint string, err error) { + return "", errors.New("抖店暂不支持此操作") +} + +func bizStatusJX2DouDian(status int) (onLine int) { + if status == model.StoreStatusDisabled || status == model.StoreStatusClosed { + return tiktok_api.StoreStatusOffline + } + return tiktok_api.StoreStatusOnline +} + +func (P *PurchaseHandler) DeleteStore(db *dao.DaoDB, storeID int, userName string) (err error) { + //TODO implement me + panic("implement me") +} + +func (P *PurchaseHandler) UpdateStoreCustomID(ctx *jxcontext.Context, vendorOrgCode, vendorStoreID string, storeID int64) (err error) { + //TODO implement me + panic("implement me") +} + +func (c *PurchaseHandler) GetOrderStatus(vendorOrgCode, vendorOrderID string) (status int, err error) { + //TODO implement me + panic("implement me") +} diff --git a/business/partner/purchase/tiktok_store/store_sku2.go b/business/partner/purchase/tiktok_store/store_sku2.go index 707d4c03e..504612266 100644 --- a/business/partner/purchase/tiktok_store/store_sku2.go +++ b/business/partner/purchase/tiktok_store/store_sku2.go @@ -307,7 +307,7 @@ func (p *PurchaseHandler) createOrUpdateStoreSkus(ctx *jxcontext.Context, storeI // spec_prices param.SpecPrices = GetSpecPrices(param.Specs, storeSku) // ProductFormatNew - productFormatNew, err := GetProductFormatNew(param.CategoryLeafId) + productFormatNew, err := GetProductFormatNew(param.CategoryLeafId, storeDetail.VendorOrgCode) if err != nil { return nil, err } @@ -371,7 +371,7 @@ func (p *PurchaseHandler) createOrUpdateStoreSkus(ctx *jxcontext.Context, storeI // spec_prices param.SpecPrices = GetSpecPrices(param.Specs, storeSku) // ProductFormatNew - productFormatNew, err := GetProductFormatNew(param.CategoryLeafId) + productFormatNew, err := GetProductFormatNew(param.CategoryLeafId, storeDetail.VendorOrgCode) if err != nil { return nil, err } diff --git a/business/partner/purchase/tiktok_store/store_sku2_utils.go b/business/partner/purchase/tiktok_store/store_sku2_utils.go index 73ca4c9db..4e2267696 100644 --- a/business/partner/purchase/tiktok_store/store_sku2_utils.go +++ b/business/partner/purchase/tiktok_store/store_sku2_utils.go @@ -13,8 +13,8 @@ import ( ) // GetProductFormatNew 获取物品属性 -func GetProductFormatNew(categoryLeftId int64) (string, error) { - category, err := api.TiktokStore.GetCatePropertyV2(categoryLeftId) +func GetProductFormatNew(categoryLeftId int64, vendorOrgCode string) (string, error) { + category, err := getAPI(vendorOrgCode, 0, "").GetCatePropertyV2(categoryLeftId) if err != nil { return "", err } diff --git a/business/partner/purchase/tiktok_store/warehouse.go b/business/partner/purchase/tiktok_store/warehouse.go new file mode 100644 index 000000000..26c5e3a48 --- /dev/null +++ b/business/partner/purchase/tiktok_store/warehouse.go @@ -0,0 +1,144 @@ +package tiktok_store + +import ( + "fmt" + warehouse_bindFencesByStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/warehouse_bindFencesByStore/request" + warehouse_bindStore_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/warehouse_bindStore/request" + warehouse_createBatch_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/warehouse_createBatch/request" + warehouse_createFence_request "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/sdk-golang/api/warehouse_createFence/request" + "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/tiktok_api" + "git.rosy.net.cn/baseapi/utils" + "git.rosy.net.cn/jx-callback/business/model" + "git.rosy.net.cn/jx-callback/business/model/dao" + "strings" +) + +// todo +// /warehouse/createBatch 批量创建区域仓 +func (P *PurchaseHandler) BatchCreateWarehouse(param warehouse_createBatch_request.WarehouseCreateBatchParam) error { + infos := []warehouse_createBatch_request.OutWarehouseListItem{} + for _, v := range param.OutWarehouseList { + info := warehouse_createBatch_request.OutWarehouseListItem{ + OutWarehouseId: v.OutWarehouseId, + Name: v.Name, + Intro: v.Intro, + AddressDetail: v.AddressDetail, + WarehouseLocation: v.WarehouseLocation, + } + infos = append(infos, info) + } + req := &warehouse_createBatch_request.WarehouseCreateBatchParam{ + OutWarehouseList: infos, + } + + resp, err := getAPI("", 0, "").BatchCreateWarehouse(req) + if err != nil { + return err + } + if resp.Data["outWarehouseId"] == false { + return fmt.Errorf("outWarehouseId:%v 出错", resp.Data["outWarehouseId"]) + } + return nil +} + +// /warehouse/bindStore 仓库绑定门店 +func (P *PurchaseHandler) BindStoreWarehouse(storeIDs []int64, outWarehouseID string) error { + param := &warehouse_bindStore_request.WarehouseBindStoreParam{ + StoreIds: storeIDs, + OutWarehouseId: outWarehouseID, + } + if _, err := getAPI("", 0, "").StoreBindWarehouse(param); err != nil { + return err + } + return nil +} + +type LocalStore struct { + Lng int `json:"-"` // 乘了10的6次方 + Lat int `json:"-"` // 乘了10的6次方 + DeliveryRangeType int8 `json:"deliveryRangeType"` // 参见相关常量定义 + DeliveryRange string `json:"deliveryRange"` // 如果DeliveryRangeType为DeliveryRangeTypePolygon,则为逗号分隔坐标,分号分隔的坐标点(坐标与Lng和Lat一样,都是整数),比如 121361504,31189308;121420555,31150238。否则为半径,单位为米 + VendorStoreID string `json:"vendorStoreID"` // 平台上门店id +} + +// /warehouse/createFence 以门店方式创建电子围栏 +func (P *PurchaseHandler) CreateFenceByStore(storeID int) (fenceID string, err error) { + var ( + db *dao.DaoDB + localStore *LocalStore + verticeses []warehouse_createFence_request.VerticesItem + ) + sqlParam := []interface{}{ + model.VendorIDDD, + } + sqlStr := ` SELECT t.lng,t.lat,t.delivery_range_type,t.delivery_range,s.vendor_store_id FROM store t + LEFT JOIN store_map s ON t.id = s.store_id + WHERE s.vendor_id= ? ` + if storeID != 0 { + sqlStr += " AND t.id = ? " + sqlParam = append(sqlParam, storeID) + } else { + return "", fmt.Errorf("storeID必填") + } + if err = dao.GetRow(db, &localStore, sqlStr, sqlParam...); err == nil { + param := &warehouse_createFence_request.WarehouseCreateFenceParam{ + FenceInfo: &warehouse_createFence_request.FenceInfo{ + OutFenceId: "京西门店:" + utils.Int2Str(storeID) + " 的电子围栏", + Shape: int32(localStore.DeliveryRangeType), + }, + } + if localStore.DeliveryRangeType == tiktok_api.ShapeCircular { + circular := &warehouse_createFence_request.Circular{ + Center: &warehouse_createFence_request.Center{ + Longitude: utils.Int2Float64(localStore.Lng), + Latitude: utils.Int2Float64(localStore.Lat), + }, + Radius: utils.Str2Float64(localStore.DeliveryRange), + } + param.FenceInfo.Circular = circular + } else if localStore.DeliveryRangeType == tiktok_api.ShapePolygon { + tempStr := strings.Split(localStore.DeliveryRange, ";") + for v := len(tempStr) - 1; v >= 0; v-- { + s2 := strings.Split(tempStr[v], ",") + vertices := warehouse_createFence_request.VerticesItem{ + Longitude: utils.Str2Float64(s2[0]), + Latitude: utils.Str2Float64(s2[1]), + } + verticeses = append(verticeses, vertices) + } + param.FenceInfo.Polygon.Vertices = verticeses + } + resp, err := getAPI("", 0, "").CreateFence(param) + if err != nil { + return "", err + } else { + return resp.FenceId, err + } + } else { + return "", err + } +} + +//直接创建电子围栏方式 +func (P *PurchaseHandler) CreateFenceDirectly(param warehouse_createFence_request.WarehouseCreateFenceParam) (fenceID string, err error) { + info := &warehouse_createFence_request.WarehouseCreateFenceParam{ + FenceInfo: param.FenceInfo, + } + resp, err := getAPI("", 0, "").CreateFence(info) + if err != nil { + return "", err + } + return resp.FenceId, err +} + +//门店直接绑定围栏 +func (P *PurchaseHandler) BindFenceByStore(storeID int64, addOutFenceIDs []string) error { + param := &warehouse_bindFencesByStore_request.WarehouseBindFencesByStoreParam{ + StoreId: storeID, + AddOutFenceIds: addOutFenceIDs, + } + if _, err := getAPI("", 0, "").BindFenceByStore(param); err != nil { + return err + } + return nil +} diff --git a/conf/app.conf b/conf/app.conf index 6bfed0357..f1c69f9a0 100644 --- a/conf/app.conf +++ b/conf/app.conf @@ -20,6 +20,7 @@ mtwmAppID2 = "5873" mtwmSecret2 = "41c479790a76f86326f89e8048964739" mtwmCallbackURL2 = "http://callback.jxc4.com" tiktokShopAppId = "7136048270014416392" +tiktokShopAppSecret = "c397aa9f-3927-47c4-8cfe-4d84e02602e0" # mtwmCookieStr = "_lxsdk_cuid=16ddced5e9a95-0a65869c427a14-48714616-15f900-16ddced5e9b2b; _hc.v=cfebbfd1-79a7-9823-d8df-77e59646cb34.1571369610; _lxsdk=16ddced5e9a95-0a65869c427a14-48714616-15f900-16ddced5e9b2b; uuid_update=true; uuid=7b28e71504f5414e382b.1579155871.1.0.0; device_uuid=!64dedf83-b510-4910-8a31-b2b13d0bdd73; pushToken=00kRvxlerO15kB0dJFWDwYuctAoe04xGMNd0r3BqvLUA*; acctId=57396785; brandId=-1; wmPoiId=-1; isOfflineSelfOpen=0; city_id=0; isChain=1; existBrandPoi=true; ignore_set_router_proxy=true; region_id=; region_version=0; newCategory=false; bsid=OyqgRLyV54i9JKP0zRCI9jPyXc4UBU-6KReDAkPIwSlljhb97JPyFUIXfYQvhlJb6G1erzHQKbvtZ2pSWOYDxQ; cityId=510100; provinceId=510000; city_location_id=0; location_id=0; igateApp=shangouepc; wpush_server_url=wss://wpush.meituan.com; token=0MScAPaSa57iwRpgpCmGLf21tiA4yU4Uy-nDZlv8wNWs*; shopCategory=food; set_info=%7B%22wmPoiId%22%3A-1%2C%22ignoreSetRouterProxy%22%3Atrue%7D; JSESSIONID=105dgww27nsy6yfp68q7wmcni; LX_SC_CONSTANT=c_shangou_online_e_znrurnrc; _lxsdk_s=17041b590ac-3d-689-a8c%7C%7C15" @@ -40,6 +41,7 @@ enableDdStoreWrite = false enableWscStoreWrite = false enableYbStoreWrite = false enableJdShopWrite = false +enableDouDianStoreWrite=false jdsCookie = "shshshfpa=13b38d4a-8ba0-df12-0012-82d9a37fb835-1573795914; shshshfpb=abYp8Dq5JobRtp2pkZa7MbA%3D%3D; __jdu=1142616513; pinId=WMIzMhF5BfL6nJp9AcA2-A; pin=shop_jxcs; unick=shop_jxcs; _tp=7FBEvLyPe%2FKcgxsfY5lRgA%3D%3D; _pst=shop_jxcs; areaId=22; ipLoc-djd=22-1930-50948-57092; user-key=3ec204b4-f204-4320-98e3-b2569c757800; cn=0; shshshfp=5d23828ee6ea3a33e1a58588db1713f8; 3AB9D23F7A4B3C9B=AK36FFYF5J6WMPRH7YTXMEX4CATHR6NAA3IQEESU2I33FEJRQ3DRLU4SZJYD2XGFLCFW43DHYP5HQKOMR4EFQSLKLA; navigation=[%22shop_jxcs%22]; __jdv=122270672|baidu|-|organic|not set|1589514011252; language=zh_CN; ceshi3.com=000; csrf_token=b84d0a5c-6288-4db4-84e1-cadf66be3bf7; mba_muid=1142616513; TrackID=1qvZk-6QSAOp1NmaouJGEx58_cFglCFv57HEfoHOezMrOnV3_FSK-5ExeYhHx97IltBADG3dvJqLIt3P57wyUW4Z2Q3Y8ITo8Cfdmlz3kykM; RT="z=1&dm=jd.com&si=mcot45862q&ss=kaf1rcqz&sl=2&tt=38t&ld=22qx&nu=b99e5a7f32b36f184614d34a1d926a39&cl=3clu&ul=3crs&hd=3cz3"; b-sec=S2JWP6CAFP7K4I6PXVBUVCO6YVXUX2JAPDHLX5RZUDE4YKCGOEXJIINB3Q4THCFCMVWZPFAYGLWLG; thor=80FAF09E9A09B6E618A68057BDFCFCB8C86E8252DC9F7D3B34572625904FBA0AB6BF053A5325612EC0407791BB05F5301356E71E8B282C40C06D0B5DF3439DEECB102A78FAFF7AC0FC4E2D1FA8DD8BBAE1A011E50B5C74F1870AD982D7BF453F470F31F2241B73AC4C25485025C2ABEBC8A538AF7257824D2FAEE300A1435175B0B451FB5C19B78D729FC83152CA3BAF; _vender_=TNK3O6PALVQGGA33SGBIUTOKL4OOE6DP6OMNVIPMAMULGTRFWUMTVWGFRUTYP4L4EPN3KP73P33BOBN5SNJFBNQB5OMQYSJ5MORGQLJS7QAPOMIN7AZD6B3ZLP2DV4JCXDI5P3KOXJ3PHLIIRZ2YVS4JSSA3JRSBACNLJSC24ELO46GIMRW53XGW36EBPLZMZP2MQCAMJNO44FKT46B7VDVT7KQTELESOOF6E377AYC3NWKQF6ICIYBW4BA4JL5QG2NHGNOHOUJDNUW3N22UF32DLFLEIQGVO2W55J6AKPPBT227XA5NO4S3NFVIUUUADGOYH56T72MTNXCILWVMN4RMUNVFMGL4ISGXJS7YILE7A2ESPAU43MISAOZM2BR53MGRB5OZSQZPV5DBDCN2OVVT3XT5N2VMFELARQNTMAJCDBGXFURSN2Q7SYULLKZEZHTYWWOI65LS5OIHLUZQKWFGMNSQF2UBSYV7FG46CWJGMVHOGV3FY4RUEVJK6BQ223QK3H3VMTHXCZOZV4GKR5EWGIZZDVUAK4B36BPA5HPBO7PXKBOEXEBX77IYBNQLCGMK72J4VKNOUPYKNB5JE5D5UN3R2MMFGLJARTL2QTC5ZRZ4PJCJZWWOV37VWLWFVAN5IGHPAYME73KTNFABM5W73XLOXJFQWTFRZEK3FCL3BLRV4UOXLBQGA34R4WUBYSZURMKTXXB7U; __jda=65775340.1142616513.1573036516.1589946171.1589952725.54; __jdb=65775340.147.1142616513|54.1589952725; __jdc=65775340; _base_=YKH2KDFHMOZBLCUV7NSRBWQUJPBI7JIMU5R3EFJ5UDHJ5LCU7R2NILKK5UJ6GLA2RGYT464UKXAI4Z6HPCTN4UQM3WHVQ4ENFP57OC2DC7JQLRXRUO5PW6B77O6UXAZ4TCNE6YVKRXISVLBYGYO44RCDDPWDA4AEL7ZLXI2SG4SOQWCP5WPWO6EFS7HEHMRWVKBRVHB33TFD4SMNBHRJCTDFHU6SZXCZD6RFXX2OORYGL5H2GYF2IIH2KKD4T72IR4F577G2E5II2OMMXYF2GDYNTS7WGAUXFEWRJ3CTKDBDWMHUKJQF4ZFOTNBBYBIZRXZYERXXIG6ATJFKID7XOR3NQ2CL6K7A2IEZV5HCBNYDPXFCM2ZMCS474KZ44S5F; _vender_new_=GI63BGTJFDBQ46CD7JXUX3HEPM4P5LEA3TJTFGW4ZGGIVOLTPK5T25EXTBLCENPUTR7E2I23YDFQ4ARO6JW3NHSWBDE73RTUKJTADIPFPLYFE3ARGJUBPHWUIONS72KRQOZC5P7PB4VPPLRHGEP7L3Z5K62L2E2MGTWHFJRQ3CAVBDYVW2Z4J6U73HW4BKKOCDAH5T6OJJKWKLBZFOTI7342QSL7YQ2E3I4T777RNZF23XGOTCP3D4INHNO5MNKT3XJZQBVHWUVZYQUXCK5QQTKWADKQUCYV3JRY6YAYOD7Z5IIKGNLREQTCPO7SYGSIS655JUGOUILFLXVZE6KCFG7ZTPRUD6VPE4KCIE4OUZSED6FTSEZHTM363E7XXCHB4NA7VLZHCQSBHDVGMRA7RM4RGJC3MOI4TJNGCLW6QKUCCZAY7XTGOTMC53TFUYERGNIH2RBULZ7UTZH5GU3TC6RWFI2QL4QTAIARA6GNVXENEOYIPZEHN222YDAJX5OBBEECAMAPNKZ3XNF5CNGDJ3DSU2ZLOCAKLFPCYTIIWPPJMCQ636F5464HS4OVFPFNIDW4OCE23JRPYP5FAL6TKHPAC3H3ZRU7WA5GKJJKBZUGIX7NEO4LZB7FJ3RZZZH3UHPQMNILD5DT2V7HVCUOVNOFBEOW5ID2ZMQ3XV264IU4MYHN64RA; _BELONG_CLIENT_=WPSC4XJXWK5USS4JNZY2X7VRLR5MCBKRSVHEXABGTHDGISIQK5YOLZUXYE7IOIM7MOKO74H6CRN6WHAAR4TMDV3XZWMXZRCRT5XRNE3V356BTOB2Y7LPK66VWQK6HPTGWVXIDXDCPVE3W5WMHAIO6AT2LX2XXVNUCXR34ZWFK6HY45CORGIKOSYDYZBF27WOKTUX6BS4FZMIJWNUX6CB4JAA25ZLF7ZEKYOO4QV5HTSBXGNRM3E242MBI6V5D4C5VJDQ3EOYCOW5BMTUJZACIBHXQFAVLRF76VQY5PNJGGJNBEZHSFYYJA3YORRT7FB5AHCOIFQKF3W5RWNUX6CB4JAA26JNMO7AYWNUPZF5HTSBXGNRM3E242MBI6V5D4C5VJDQ3EOYCOW5BWZDKMOJ5BS6II53ERY6ALV3ZWPF42L4CPUHEGPYIII35KDC4FCNVCORCXFD6IVNLBEDPB2GGP4UHWNRUDOQBDIW7RZJXBA2WV5ANZOTEGUCDWYRVQS2YUTIZNZ276PRYG4N56V6YTII7MBKBC7LYHO7C555HTSBXGNRM3E466AYN67DHWVM5HQFJ4NFDO5BTOKMOS5L2CXFVYDR2FCOILVYPEI; _lvtc_=5ZH3OJ7CWYNVGEKDRC32XTFXGY" diff --git a/controllers/tictok_callback.go b/controllers/tictok_callback.go index fb97d1a83..3dee7a2a8 100644 --- a/controllers/tictok_callback.go +++ b/controllers/tictok_callback.go @@ -39,7 +39,6 @@ func MsgFail() *TicktockRes { } func (c *TicTocController) TiktokMsg() { - //if c.Ctx.Input.Method() == http.MethodPost { call, refund, payType, err := api.TiktokApi.GetCallbackMsg(getPayInfo(c.Ctx)) globals.SugarLogger.Debugf("tictok callback callbackResponse:%s", utils.Format4Output(call, true)) if err != nil || call == nil { @@ -55,9 +54,6 @@ func (c *TicTocController) TiktokMsg() { } c.Data["json"] = MsgSuccess() c.ServeJSON() - //} else { - // c.Abort("404") - //} } func getPayInfo(ctx *context.Context) *http.Request { diff --git a/controllers/tiktok_store.go b/controllers/tiktok_store.go index 6a820036a..e6980a039 100644 --- a/controllers/tiktok_store.go +++ b/controllers/tiktok_store.go @@ -1,11 +1,15 @@ package controllers import ( + "encoding/json" "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/tiktok_api" + "git.rosy.net.cn/jx-callback/business/jxstore/common" + "git.rosy.net.cn/jx-callback/business/model" "git.rosy.net.cn/jx-callback/business/partner/purchase/tiktok_store" "git.rosy.net.cn/jx-callback/globals" "git.rosy.net.cn/jx-callback/globals/api" "github.com/astaxie/beego/server/web" + "time" ) type TiktokController struct { @@ -24,7 +28,7 @@ func (t *TiktokController) CallbackTiktokOrderMsg() { // 2.参数解析 orderStatus, resp := api.TiktokStore.CreateOrderCallback(t.Ctx.Request) - globals.SugarLogger.Debug("美团订单回调数据打印测试===========", orderStatus) + globals.SugarLogger.Debug("抖音订单回调数据打印测试===========", orderStatus) if resp.Code != 0 { t.Data["json"] = resp t.ServeJSON() @@ -46,3 +50,48 @@ func (t *TiktokController) CallbackTiktokOrderMsg() { t.ServeJSON() } + +// CallbackTiktokTokenMsg 抖音用户授权 +func (c *TiktokController) CallbackTiktokTokenMsg() { + code := c.Ctx.Request.URL.Query().Get("code") + globals.SugarLogger.Debugf("tictok callback callbackResponse:%s", code) + result, err := api.TiktokStore.CreateToken(code) + if err != nil { + globals.SugarLogger.Debugf("tictok callback create token:%s", err) + c.Data["json"] = tiktok_api.CallbackResponse{Code: tiktok_api.CallbackFailCode, Msg: tiktok_api.CallbackFail} + c.ServeJSON() + return + } + + result.ExpiresIn += time.Now().Unix() + data, err := json.Marshal(result) + if err != nil { + globals.SugarLogger.Debugf("tictok callback Marshal token:%s", err) + c.Data["json"] = tiktok_api.CallbackResponse{Code: tiktok_api.CallbackFailCode, Msg: tiktok_api.CallbackFail} + c.ServeJSON() + return + } + + param := &model.VendorOrgCode{ + VendorID: model.VendorIDDD, + VendorOrgCode: result.ShopId, + Comment: "抖音授权", + VendorType: "platform", + IsJxCat: 1, + IsOpen: 1, + EmpowerURL: "", + StoreBrandName: result.ShopName, + Token: string(data), + AppKey: "", // web.AppConfig.DefaultString("tiktokShopAppId", "7136048270014416392"), + AppSecret: "", // web.AppConfig.DefaultString("tiktokShopAppSecret", "c397aa9f-3927-47c4-8cfe-4d84e02602e0") + } + if err := common.AddVendorOrgCode(nil, param); err != nil { + globals.SugarLogger.Debugf("tictok callback insert token:%s", err) + c.Data["json"] = tiktok_api.CallbackResponse{Code: tiktok_api.CallbackFailCode, Msg: tiktok_api.CallbackFail} + c.ServeJSON() + return + } + c.Data["json"] = tiktok_api.CallbackResponse{Code: tiktok_api.CallbackSuccessCode, Msg: tiktok_api.CallbackSuccess} + c.ServeJSON() + +} diff --git a/globals/api/api.go b/globals/api/api.go index 329690b5e..f09f2650b 100644 --- a/globals/api/api.go +++ b/globals/api/api.go @@ -6,6 +6,7 @@ import ( "git.rosy.net.cn/baseapi/platformapi/qywxapi" "git.rosy.net.cn/baseapi/platformapi/tiktok" tiktokShop "git.rosy.net.cn/baseapi/platformapi/tiktok_shop/tiktok_api" + "time" "git.rosy.net.cn/baseapi/platformapi/fnpsapi" @@ -112,11 +113,12 @@ var ( Cacher cache.ICacher SMSClient *aliyunsmsclient.SmsClient - TiktokApi *tiktok.API // 抖音api - TiktokJXDJApi *tiktok.API //抖音京西到家api - TiktokApiID string //抖音商城ID - TiktokJXDJApiID string //抖音京西到家ID - TiktokStore *tiktokShop.API // 抖店 + TiktokApi *tiktok.API // 抖音api + TiktokJXDJApi *tiktok.API //抖音京西到家api + TiktokApiID string //抖音商城ID + TiktokJXDJApiID string //抖音京西到家ID + TiktokStore *tiktokShop.API // 抖店 + EnterpriseChatHeadApi *enterprise.API // 企业微信api EnterpriseChatMin *enterprise.API // 企业微信小程序api ) @@ -308,7 +310,7 @@ func Init() { TiktokJXDJApi = tiktok.New(beego.AppConfig.DefaultString("tiktokJXDJSecret", ""), beego.AppConfig.DefaultString("TiktokJXDJApiID", "")) } // 抖店 - TiktokStore = tiktokShop.New(beego.AppConfig.DefaultString("key", ""), beego.AppConfig.DefaultString("sercret", ""), "") + TiktokStore = tiktokShop.New(beego.AppConfig.DefaultString("tiktokShopAppId", ""), beego.AppConfig.DefaultString("tiktokShopAppSecret", ""), "") EnterpriseChatHeadApi = enterprise.New("ww9a156bfa070e1857", "0jBdCjSmoFiOoHIXyeCK9VbGQ82fVNJZ8uMl6JNN7X4") // 通讯录 EnterpriseChatMin = enterprise.NewMin("ww9a156bfa070e1857", "JQsEmSTltHhNgdPIT320YJFphiYmRs-YZa-rCBwplss") // 小程序 } diff --git a/globals/api/apimanager/apimanager.go b/globals/api/apimanager/apimanager.go index 461aab39d..073ccfaef 100644 --- a/globals/api/apimanager/apimanager.go +++ b/globals/api/apimanager/apimanager.go @@ -65,7 +65,11 @@ func (a *APIManager) GetAPI(vendorID int, appOrgCode string) (pfAPI interface{}) case model.VendorIDTT: pfAPI = api.TiktokApi case model.VendorIDDD: - pfAPI = api.TiktokStore + tiktokApi := api.TiktokStore + codes, _ := dao.GetVendorOrgCode(db, vendorID, appOrgCode, "platform") + code := codes[0] + tiktokApi.SetRefreshToken(code.Token) + pfAPI = tiktokApi } return pfAPI } diff --git a/globals/globals.go b/globals/globals.go index b40e5c4dc..bbe8ead96 100644 --- a/globals/globals.go +++ b/globals/globals.go @@ -22,11 +22,11 @@ var ( EnableEbaiStoreWrite bool EnableElmStoreWrite bool EnableMtwmStoreWrite bool - EnableDdStoreWrite bool EnableWscStoreWrite bool EnablePendingChange bool EnableYbStoreWrite bool EnableJdShopWrite bool //京东商城 + EnableDdStoreWrite bool QiniuBucket string WeimobCallbackURL string diff --git a/main.go b/main.go index 27c30da8f..c58b34378 100644 --- a/main.go +++ b/main.go @@ -158,9 +158,11 @@ func main() { globals.SugarLogger.Errorf("RefreshPushToken failed with error:%s", err) return } - if err := tasks.RefreshFnToken(); err != nil { - globals.SugarLogger.Errorf("RefreshFnToken failed with error:%s", err) - return + if web.BConfig.RunMode != "jxgy" { + if err := tasks.RefreshFnToken(); err != nil { + globals.SugarLogger.Errorf("RefreshFnToken failed with error:%s", err) + return + } } //if err := tasks.RefreshTiktokToken(); err != nil { // globals.SugarLogger.Errorf("RefreshTiktokToken failed with error:%s", err)