package jdapi import ( "errors" "fmt" "git.rosy.net.cn/baseapi/utils" ) const ( MaxStoreSkuBatchSize = 50 MaxStockQty = 100000000 MaxAddByStoreAndSkusCount = 30 // 批量置顶商品排序接口的最大个数 ) type SkuPriceInfo struct { OutSkuId string `json:"outSkuId"` Price int `json:"price"` } type SkuStock struct { OutSkuId string `json:"outSkuId"` StockQty int `json:"stockQty"` } type QueryStockRequest struct { StationNo string `json:"stationNo"` SkuId int64 `json:"skuId"` DoSale int `json:"doSale"` //可售状态(0:可售,1:不可售) } type StockVendibility struct { OutSkuId string `json:"outSkuId"` DoSale bool `json:"doSale"` // 可售状态(true:可售,false:不可售) } type BaseStockCenterRequest struct { StationNo string `json:"stationNo"` SkuId int64 `json:"skuId"` } type SkuIdEntity struct { OutSkuId string `json:"outSkuId"` } type StorePriceInfo struct { MarketPrice int64 `json:"marketPrice"` Pin string `json:"pin"` Price int64 `json:"price"` PromoteVipPrice int64 `json:"promoteVipPrice"` SkuID int64 `json:"skuId"` StationNo string `json:"stationNo"` VenderID string `json:"venderId"` VipPrice int64 `json:"vipPrice"` } type QueryStockResponse struct { SkuID int64 `json:"skuId"` StationNo string `json:"stationNo"` UsableQty int `json:"usableQty"` LockQty int `json:"lockQty"` OrderQty int `json:"orderQty"` Vendibility int `json:"vendibility"` } type UpdateVendibilityResponse struct { OutSkuID string `json:"outSkuId"` Code int `json:"code"` Msg string `json:"msg"` SkuID int64 `json:"skuId"` CurrentQty int `json:"currentQty"` LockQty int `json:"lockQty"` OrderQty int `json:"orderQty"` UsableQty int `json:"usableQty"` Vendibility int `json:"vendibility"` } type StoreSkuBatchUpdateResponse struct { OutSkuID string `json:"outSkuId" json2:"outSkuId"` Code int `json:"code" json2:"errorCode"` Msg string `json:"msg" json2:"errorMessage"` // UpdateVendibility会返回以下字段 SkuID int64 `json:"skuId"` StationNo string `json:"stationNo"` BusinessNo int `json:"businessNo"` CreatePin string `json:"createPin"` StockQty int `json:"stockQty"` StockSource int `json:"stockSource"` UpdatePin string `json:"updatePin"` Vendibility int `json:"vendibility"` } // 传入为数组的,最多一次为50个 // 有好些功能有两个类似的函数,一个为到家ID,一个为商家ID,建议都只用商家ID的那个,因为: // 1,这类函数一般可以批量操作 // 2,这类函数一般可以记录操作人员 // 根据商家商品编码和商家门店编码批量修改门店价格接口 // https://opendj.jd.com/staticnew/widgets/resources.html?groupid=205&apiid=fcbf346648a54d03b92dec8fa62ea643 func (a *API) UpdateVendorStationPrice(trackInfo string, outStationNo, stationNo string, skuPriceInfoList []*SkuPriceInfo) (responseList []*StoreSkuBatchUpdateResponse, err error) { jdParams := map[string]interface{}{ "skuPriceInfoList": skuPriceInfoList, } if outStationNo != "" { jdParams["outStationNo"] = outStationNo } else { jdParams["stationNo"] = stationNo } result, err := a.AccessAPINoPage2("venderprice/updateStationPrice", jdParams, nil, nil, genNoPageResultParser("code", "msg", "result", "0"), trackInfo) if result != nil { var err2 error if responseList, err2 = a.handleBatchOpResult(outStationNo, stationNo, len(skuPriceInfoList), err, result, "json2"); err2 != nil && err == nil { err = err2 } } return responseList, err } // 根据到家商品编码和到家门店编码修改门店价格接口 // https://opendj.jd.com/staticnew/widgets/resources.html?groupid=205&apiid=45f83ef7c6e74dad94b6b68d3c50b673 // 单商品用此接口 func (a *API) UpdateStationPrice(trackInfo string, skuId int64, stationNo string, price int) (string, error) { jdParams := map[string]interface{}{ "skuId": skuId, "stationNo": stationNo, "price": price, } result, err := a.AccessAPINoPage2("price/updateStationPrice", jdParams, nil, nil, nil, trackInfo) if err == nil && result != nil { return utils.Interface2String(result), nil } return "", err } // 根据到家商品编码和到家门店编码批量查询商品门店价格信息接口 // https://opendj.jd.com/staticnew/widgets/resources.html?groupid=205&apiid=21ccd5a00d3a4582b4c9a8ef0ae238fc func (a *API) GetStationInfoList(stationNo string, skuIds []int64) (priceInfo []*StorePriceInfo, err error) { jdParams := map[string]interface{}{ "skuIds": skuIds, "stationNo": stationNo, } result, err := a.AccessAPINoPage("price/getStationInfoList", jdParams, nil, nil, genNoPageResultParser("code", "detail", "result", "0")) if err == nil && result != nil { err = JdMap2StructByJson(result, &priceInfo, false) } return priceInfo, err } func (a *API) handleBatchOpResult(outStationNo, stationNo string, batchCount int, inErr error, result interface{}, tagName string) (responseList []*StoreSkuBatchUpdateResponse, err error) { if result != nil { if err = utils.Map2Struct(result, &responseList, true, tagName, JavaDateHook); err == nil { var failedList []*StoreSkuBatchUpdateResponse for _, v := range responseList { if v.Code != 0 { failedList = append(failedList, v) } } var err2 *utils.ErrorWithCode if len(failedList) >= batchCount { err2 = utils.NewErrorCode(string(utils.MustMarshal(failedList)), ResponseCodeAccessFailed, 1) // 此错误基本用不到 } else if len(failedList) > 0 { // 部分失败 err2 = utils.NewErrorCode(string(utils.MustMarshal(failedList)), ResponseInnerCodePartialFailed, 1) } if err2 != nil { if stationNo != "" { err2.AddPrefixMsg(fmt.Sprintf("stationNo:%s", stationNo)) } else if outStationNo != "" { err2.AddPrefixMsg(fmt.Sprintf("outStationNo:%s", outStationNo)) } err = err2 } } } return responseList, err } // 根据商家商品编码和商家门店编码批量修改现货库存接口 // https://opendj.jd.com/staticnew/widgets/resources.html?groupid=200&apiid=10812f9fc7ee4564b552f19270a7e92e func (a *API) BatchUpdateCurrentQtys(trackInfo, outStationNo, stationNo string, skuStockList []*SkuStock, userPin string) (responseList []*StoreSkuBatchUpdateResponse, err error) { if (outStationNo == "" && stationNo == "") || (outStationNo != "" && stationNo != "") { return nil, errors.New("outStationNo and stationNo can not all be empty or have value") } jdParams := map[string]interface{}{ "skuStockList": skuStockList, "userPin": utils.GetAPIOperator(userPin), } if outStationNo != "" { jdParams["outStationNo"] = outStationNo } else { jdParams["stationNo"] = stationNo } result, err := a.AccessAPINoPage2("stock/batchUpdateCurrentQtys", jdParams, nil, nil, genNoPageResultParser("retCode", "retMsg", "data", "0"), trackInfo) if result != nil { var err2 error if responseList, err2 = a.handleBatchOpResult(outStationNo, stationNo, len(skuStockList), err, result, ""); err2 != nil && err == nil { err = err2 } } return responseList, err } // 根据商家商品编码和商家门店编码更新门店现货库存接口 // https://opendj.jd.com/staticnew/widgets/resources.html?groupid=200&apiid=a78664d4ead349da95d2f4576ed18d7f // 此接口基本可以不用 func (a *API) StockUpdate(trackInfo string, outStationNo string, outSkuID string, currentQty int) error { // !这个接口的stationNo与skuId好像本身就写错了的 jdParams := map[string]interface{}{ "stationNo": outStationNo, "skuId": outSkuID, "currentQty": currentQty, } _, err := a.AccessAPINoPage2("stock/update", jdParams, nil, nil, genNoPageResultParser("retCode", "retMsg", "", "0"), trackInfo) if err == nil { return nil } return err } // 根据到家商品编码和到家门店编码更新门店现货库存 // https://openo2o.jddj.com/staticnew/widgets/resources.html?groupid=200&apiid=af70e699d4974e1683128742018f6381 // 单商品用此接口 func (a *API) UpdateCurrentQty(trackInfo string, stationNo string, skuID int64, currentQty int) error { jdParams := map[string]interface{}{ "stationNo": stationNo, "skuId": skuID, "currentQty": currentQty, } _, err := a.AccessAPINoPage2("update/currentQty", jdParams, nil, nil, genNoPageResultParser("retCode", "retMsg", "", "0"), trackInfo) if err == nil { return nil } return err } // 根据到家商品编码和到家门店编码批量修改门店商品可售状态接口 // https://opendj.jd.com/staticnew/widgets/resources.html?groupid=200&apiid=b783a508e2cf4aca94681e4eed9af5bc // 尽量不用这个接口,用下面那个,原因是这个不支持设置操作人,BatchUpdateVendibility可以 func (a *API) UpdateVendibility(trackInfo string, listBaseStockCenterRequest []*QueryStockRequest) (responseList []*StoreSkuBatchUpdateResponse, err error) { jdParams := map[string]interface{}{ "listBaseStockCenterRequest": listBaseStockCenterRequest, } result, err := a.AccessAPINoPage2("stock/updateVendibility", jdParams, nil, nil, genNoPageResultParser("retCode", "retMsg", "data", "0"), trackInfo) if result != nil { var err2 error if responseList, err2 = a.handleBatchOpResult("", listBaseStockCenterRequest[0].StationNo, len(listBaseStockCenterRequest), err, result, ""); err2 != nil && err == nil { err = err2 } } return responseList, err } // 根据商家商品编码和门店编码批量修改门店商品可售状态接口 // https://opendj.jd.com/staticnew/widgets/resources.html?groupid=200&apiid=ac6f559ebabf4b70bc423687638e07c1 func (a *API) BatchUpdateVendibility(trackInfo, outStationNo, stationNo string, stockVendibilityList []*StockVendibility, userPin string) (responseList []*StoreSkuBatchUpdateResponse, err error) { if (outStationNo == "" && stationNo == "") || (outStationNo != "" && stationNo != "") { return nil, errors.New("outStationNo and stationNo can not all be empty or have value") } jdParams := map[string]interface{}{ "stockVendibilityList": stockVendibilityList, "userPin": utils.GetAPIOperator(userPin), } if outStationNo != "" { jdParams["outStationNo"] = outStationNo } else { jdParams["stationNo"] = stationNo } // 此函数在全部失败时,err仍然返回成功 result, err := a.AccessAPINoPage2("stock/batchUpdateVendibility", jdParams, nil, nil, genNoPageResultParser("retCode", "retMsg", "data", "0"), trackInfo) if result != nil { var err2 error if responseList, err2 = a.handleBatchOpResult(outStationNo, stationNo, len(stockVendibilityList), err, result, ""); err2 != nil && err == nil { err = err2 } } return responseList, err } // 根据到家商品编码和门店编码批量查询商品库存及可售状态信息接口 // https://opendj.jd.com/staticnew/widgets/resources.html?groupid=200&apiid=bc6ad75e8fd34580856e06b5eb149aad // 尽量不用这个接口,用下面那个 func (a *API) QueryOpenUseable(listBaseStockCenterRequest []*BaseStockCenterRequest) (stockResponse []*QueryStockResponse, err error) { jdParams := map[string]interface{}{ "listBaseStockCenterRequest": listBaseStockCenterRequest, } result, err := a.AccessAPINoPage("stock/queryOpenUseable", jdParams, nil, nil, genNoPageResultParser("retCode", "retMsg", "data", "0")) if err == nil && result != nil { err = JdMap2StructByJson(result, &stockResponse, false) } return stockResponse, err } // 根据商家商品编码和门店编码批量查询商品库存及可售状态信息接口 // https://opendj.jd.com/staticnew/widgets/resources.html?groupid=200&apiid=ba70316bb84f425f8c088d3c19b2570d func (a *API) QueryStockCenter(outStationNo string, skuIds []*SkuIdEntity, userPin string) (vendibilityResponse []*UpdateVendibilityResponse, err error) { jdParams := map[string]interface{}{ "outStationNo": outStationNo, "skuIds": skuIds, "userPin": utils.GetAPIOperator(userPin), } result, err := a.AccessAPINoPage("stock/queryStockCenter", jdParams, nil, nil, genNoPageResultParser("retCode", "retMsg", "data", "0")) if err == nil && result != nil { err = JdMap2StructByJson(result, &vendibilityResponse, false) } return vendibilityResponse, err } // 批量置顶商品排序接口 // https://opendj.jd.com/staticnew/widgets/resources.html?groupid=180&apiid=a7677f1a75984ed3a6ea3d4827f5a6b4 func (a *API) AddByStoreAndSkus(stationNo int64, skuIDs []int64) (err error) { jdParams := map[string]interface{}{ "storeId": stationNo, "skuIds": skuIDs, } _, err = a.AccessAPINoPage("OrgSortService/addByStoreAndSkus", jdParams, nil, nil, genNoPageResultParser("status", "message", "", "200")) return err }