- refactor jxcontent and tasksch (remove dependency from jxcontent to tasksch)

- send dingding msg to user when async task finished
This commit is contained in:
gazebo
2019-03-22 15:04:28 +08:00
parent 0f5445020a
commit 25ac631c5c
31 changed files with 1527 additions and 1488 deletions

View File

@@ -387,3 +387,7 @@ func DisableUser(userID, operatorUserName string) (err error) {
}
return err
}
func GetUserBindAuthInfo(userID string) (authList []*model.AuthBind, err error) {
return dao.GetUserBindAuthInfo(dao.GetDB(), userID)
}

View File

@@ -41,7 +41,7 @@ func SendStoreMessage(ctx *jxcontext.Context, title, content string, storeIDs []
}
dao.Commit(db)
rootTask := tasksch.NewParallelTask("SendStoreMessage", nil, ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
rootTask := tasksch.NewParallelTask("SendStoreMessage", nil, ctx, func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
db := dao.GetDB()
msgStatus := batchItemList[0].(*model.MessageStatus)
if err = weixinmsg.NotifyStoreMessage(msgStatus.StoreID, msgStatus.MessageID, msgStatus.ID, msg.Title, msg.Content); err == nil {

View File

@@ -750,40 +750,40 @@ func RefreshMissingDadaStores(ctx *jxcontext.Context, storeID int, isAsync, isCo
if err != nil {
return "", err
}
task := tasksch.NewParallelTask("RefreshMissingDadaStores", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
storeDetail := batchItemList[0].(*dao.StoreDetail2)
_, err = api.DadaAPI.ShopDetail(utils.Int2Str(storeDetail.ID))
if err != nil {
if codeErr, ok := err.(*utils.ErrorWithCode); ok && codeErr.IntCode() == dadaapi.ResponseCodeShopNotExist {
_, err = api.DadaAPI.ShopAdd(utils.Int2Str(storeDetail.ID), composeDadaStoreName(storeDetail), dadaapi.BusinessTypeConvStore, storeDetail.CityName,
storeDetail.DistrictName, storeDetail.Address, jxutils.IntCoordinate2Standard(storeDetail.Lng), jxutils.IntCoordinate2Standard(storeDetail.Lat),
storeDetail.Tel1, storeDetail.Tel1, nil)
task := tasksch.NewParallelTask("RefreshMissingDadaStores", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
storeDetail := batchItemList[0].(*dao.StoreDetail2)
_, err = api.DadaAPI.ShopDetail(utils.Int2Str(storeDetail.ID))
if err != nil {
if codeErr, ok := err.(*utils.ErrorWithCode); ok && codeErr.IntCode() == dadaapi.ResponseCodeShopNotExist {
_, err = api.DadaAPI.ShopAdd(utils.Int2Str(storeDetail.ID), composeDadaStoreName(storeDetail), dadaapi.BusinessTypeConvStore, storeDetail.CityName,
storeDetail.DistrictName, storeDetail.Address, jxutils.IntCoordinate2Standard(storeDetail.Lng), jxutils.IntCoordinate2Standard(storeDetail.Lat),
storeDetail.Tel1, storeDetail.Tel1, nil)
}
} else {
params := map[string]interface{}{
"station_name": composeDadaStoreName(storeDetail),
"business": dadaapi.BusinessTypeConvStore,
"city_name": storeDetail.CityName,
"area_name": storeDetail.DistrictName,
"station_address": storeDetail.Address,
"lng": jxutils.IntCoordinate2Standard(storeDetail.Lng),
"lat": jxutils.IntCoordinate2Standard(storeDetail.Lat),
"contact_name": storeDetail.Tel1,
"phone": storeDetail.Tel1,
}
err = api.DadaAPI.ShopUpdate(utils.Int2Str(storeDetail.ID), params)
}
} else {
params := map[string]interface{}{
"station_name": composeDadaStoreName(storeDetail),
"business": dadaapi.BusinessTypeConvStore,
"city_name": storeDetail.CityName,
"area_name": storeDetail.DistrictName,
"station_address": storeDetail.Address,
"lng": jxutils.IntCoordinate2Standard(storeDetail.Lng),
"lat": jxutils.IntCoordinate2Standard(storeDetail.Lat),
"contact_name": storeDetail.Tel1,
"phone": storeDetail.Tel1,
if err == nil {
db := dao.GetDB()
_, err = AddStoreCourierMap(ctx, db, storeDetail.ID, model.VendorIDDada, &model.StoreCourierMap{
VendorStoreID: utils.Int2Str(storeDetail.ID),
Status: model.StoreStatusOpened,
})
}
err = api.DadaAPI.ShopUpdate(utils.Int2Str(storeDetail.ID), params)
}
if err == nil {
db := dao.GetDB()
_, err = AddStoreCourierMap(ctx, db, storeDetail.ID, model.VendorIDDada, &model.StoreCourierMap{
VendorStoreID: utils.Int2Str(storeDetail.ID),
Status: model.StoreStatusOpened,
})
}
return nil, err
}, storeList)
ctx.SetTaskOrAddChild(task, nil)
tasksch.ManageTask(task).Run()
return nil, err
}, storeList)
tasksch.HandleTask(task, nil, true).Run()
hint = task.ID
if !isAsync {
_, err = task.GetResult(0)

View File

@@ -130,29 +130,29 @@ func (v *VendorSync) GetSingleStoreHandler(vendorID int) partner.ISingleStoreHan
func (v *VendorSync) syncCategories(ctx *jxcontext.Context, parentTask tasksch.ITask, multiStoresHandler partner.IMultipleStoresHandler, db *dao.DaoDB, cats []*model.SkuCategory, userName string) (err error) {
syncStatusFieldName := dao.GetSyncStatusStructField(model.VendorNames[multiStoresHandler.GetVendorID()])
task := tasksch.NewParallelTask("syncCategories", nil, userName, func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (interface{}, error) {
cat := batchItemList[0].(*model.SkuCategory)
updateFields := []string{syncStatusFieldName}
syncStatus := jxutils.GetObjFieldByName(cat, syncStatusFieldName).(int8)
if (syncStatus & model.SyncFlagDeletedMask) != 0 { //删除
err = multiStoresHandler.DeleteCategory(db, cat, userName)
} else if (syncStatus & model.SyncFlagNewMask) != 0 { // 新增
err = multiStoresHandler.CreateCategory(db, cat, userName)
updateFields = append(updateFields, dao.GetVendorThingIDStructField(model.VendorNames[multiStoresHandler.GetVendorID()]))
} else if (syncStatus & model.SyncFlagModifiedMask) != 0 { // 修改
err = multiStoresHandler.UpdateCategory(db, cat, userName)
if intErr, ok := err.(*utils.ErrorWithCode); ok && intErr.IntCode() == -3 {
err = nil
task := tasksch.NewParallelTask("syncCategories", nil, ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (interface{}, error) {
cat := batchItemList[0].(*model.SkuCategory)
updateFields := []string{syncStatusFieldName}
syncStatus := jxutils.GetObjFieldByName(cat, syncStatusFieldName).(int8)
if (syncStatus & model.SyncFlagDeletedMask) != 0 { //删除
err = multiStoresHandler.DeleteCategory(db, cat, userName)
} else if (syncStatus & model.SyncFlagNewMask) != 0 { // 新增
err = multiStoresHandler.CreateCategory(db, cat, userName)
updateFields = append(updateFields, dao.GetVendorThingIDStructField(model.VendorNames[multiStoresHandler.GetVendorID()]))
} else if (syncStatus & model.SyncFlagModifiedMask) != 0 { // 修改
err = multiStoresHandler.UpdateCategory(db, cat, userName)
if intErr, ok := err.(*utils.ErrorWithCode); ok && intErr.IntCode() == -3 {
err = nil
}
}
}
if err == nil {
jxutils.SetObjFieldByName(cat, syncStatusFieldName, int8(0))
_, err = dao.UpdateEntity(db, cat, updateFields...)
}
return nil, err
}, cats)
ctx.SetTaskOrAddChild(task, parentTask)
task.Run()
if err == nil {
jxutils.SetObjFieldByName(cat, syncStatusFieldName, int8(0))
_, err = dao.UpdateEntity(db, cat, updateFields...)
}
return nil, err
}, cats)
tasksch.HandleTask(task, parentTask, false).Run()
_, err = task.GetResult(0)
return err
}
@@ -212,14 +212,15 @@ func (v *VendorSync) SyncStore(ctx *jxcontext.Context, db *dao.DaoDB, vendorID,
loopMapInfo := batchItemList[0].(*LoopStoreMapInfo)
handler := v.GetStoreHandler(loopMapInfo.VendorID)
if len(loopMapInfo.StoreMapList) > 1 {
loopStoreTask := tasksch.NewParallelTask(fmt.Sprintf("SyncStore loop store %s", model.VendorChineseNames[loopMapInfo.VendorID]), nil, ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
storeMap := batchItemList[0].(*model.StoreMap)
if err = handler.UpdateStore(db, storeMap.StoreID, userName); err == nil {
storeMap.SyncStatus = 0
_, err = dao.UpdateEntity(db, storeMap, model.FieldSyncStatus)
}
return nil, err
}, loopMapInfo.StoreMapList)
loopStoreTask := tasksch.NewParallelTask(fmt.Sprintf("SyncStore loop store %s", model.VendorChineseNames[loopMapInfo.VendorID]), nil, ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
storeMap := batchItemList[0].(*model.StoreMap)
if err = handler.UpdateStore(db, storeMap.StoreID, userName); err == nil {
storeMap.SyncStatus = 0
_, err = dao.UpdateEntity(db, storeMap, model.FieldSyncStatus)
}
return nil, err
}, loopMapInfo.StoreMapList)
t.AddChild(loopStoreTask).Run()
_, err = loopStoreTask.GetResult(0)
return nil, err
@@ -262,51 +263,52 @@ func (v *VendorSync) SyncSku(ctx *jxcontext.Context, db *dao.DaoDB, nameID, skuI
err := dao.GetRows(db, &skuNameList, sql, sqlParams...)
if err == nil && len(skuNameList) > 0 {
// todo 同一skuName下的sku顺序处理的原因是京东SPU特殊类型必须要序列化同步才能正常处理, db可能会有多线程问题
task := tasksch.NewParallelTask("SyncSku loop sku", tasksch.NewParallelConfig().SetParallelCount(10).SetIsContinueWhenError(isContinueWhenError), userName, func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (interface{}, error) {
skuName := batchItemList[0].(*model.SkuName)
var skuList []*model.Sku
if err = dao.GetRows(db, &skuList, fmt.Sprintf(`
task := tasksch.NewParallelTask("SyncSku loop sku", tasksch.NewParallelConfig().SetParallelCount(10).SetIsContinueWhenError(isContinueWhenError), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (interface{}, error) {
skuName := batchItemList[0].(*model.SkuName)
var skuList []*model.Sku
if err = dao.GetRows(db, &skuList, fmt.Sprintf(`
SELECT *
FROM sku
WHERE name_id = ? AND %s_sync_status <> 0
ORDER BY IF(spec_unit IN('kg', 'L'), 1000, 1) * spec_quality
`, dbField), skuName.ID); err == nil && len(skuList) > 0 {
for _, sku := range skuList {
syncStatus := jxutils.GetObjFieldByName(sku, syncStatusFieldName).(int8)
if (skuID == -1 || skuID == sku.ID) && (syncStatus != 0) {
updateFields := []string{syncStatusFieldName}
if syncStatus&model.SyncFlagDeletedMask != 0 { // 删除
err = multiStoresHandler.DeleteSku(db, sku, userName)
} else if syncStatus&model.SyncFlagNewMask != 0 { // 新增
if err = multiStoresHandler.CreateSku(db, sku, userName); err == nil {
var tmpStruct struct {
MaxIndex int
for _, sku := range skuList {
syncStatus := jxutils.GetObjFieldByName(sku, syncStatusFieldName).(int8)
if (skuID == -1 || skuID == sku.ID) && (syncStatus != 0) {
updateFields := []string{syncStatusFieldName}
if syncStatus&model.SyncFlagDeletedMask != 0 { // 删除
err = multiStoresHandler.DeleteSku(db, sku, userName)
} else if syncStatus&model.SyncFlagNewMask != 0 { // 新增
if err = multiStoresHandler.CreateSku(db, sku, userName); err == nil {
var tmpStruct struct {
MaxIndex int
}
// todo hard code 得到京东spu中sku的顺序以方便以后修改销售属性这个必须要每次重新从数据库取
if dao.GetRow(db, &tmpStruct, "SELECT MAX(sku_index) max_index FROM sku WHERE name_id = ? AND jd_id > 0 AND jd_id < 4024012631406 ", sku.NameID) == nil {
sku.SkuIndex = tmpStruct.MaxIndex + 1
updateFields = append(updateFields, "SkuIndex")
}
updateFields = append(updateFields, dao.GetVendorThingIDStructField(model.VendorNames[multiStoresHandler.GetVendorID()]))
}
// todo hard code 得到京东spu中sku的顺序以方便以后修改销售属性这个必须要每次重新从数据库取
if dao.GetRow(db, &tmpStruct, "SELECT MAX(sku_index) max_index FROM sku WHERE name_id = ? AND jd_id > 0 AND jd_id < 4024012631406 ", sku.NameID) == nil {
sku.SkuIndex = tmpStruct.MaxIndex + 1
updateFields = append(updateFields, "SkuIndex")
}
updateFields = append(updateFields, dao.GetVendorThingIDStructField(model.VendorNames[multiStoresHandler.GetVendorID()]))
} else if syncStatus&model.SyncFlagModifiedMask != 0 { // 修改
err = multiStoresHandler.UpdateSku(db, sku, userName)
}
} else if syncStatus&model.SyncFlagModifiedMask != 0 { // 修改
err = multiStoresHandler.UpdateSku(db, sku, userName)
}
if err == nil {
jxutils.SetObjFieldByName(sku, syncStatusFieldName, int8(0))
if _, err = dao.UpdateEntity(db, sku, updateFields...); err != nil {
break
if err == nil {
jxutils.SetObjFieldByName(sku, syncStatusFieldName, int8(0))
if _, err = dao.UpdateEntity(db, sku, updateFields...); err != nil {
break
}
}
}
}
}
}
if err == nil {
jxutils.SetObjFieldByName(skuName, syncStatusFieldName, int8(0))
_, err = dao.UpdateEntity(db, skuName, syncStatusFieldName)
}
return nil, err
}, skuNameList)
if err == nil {
jxutils.SetObjFieldByName(skuName, syncStatusFieldName, int8(0))
_, err = dao.UpdateEntity(db, skuName, syncStatusFieldName)
}
return nil, err
}, skuNameList)
t.AddChild(task).Run()
_, err = task.GetResult(0)
}
@@ -320,11 +322,12 @@ func (v *VendorSync) SyncStoresCategory(ctx *jxcontext.Context, db *dao.DaoDB, v
loopMapInfo := batchItemList[0].(*LoopStoreMapInfo)
if handler := v.GetSingleStoreHandler(loopMapInfo.VendorID); handler != nil {
if len(loopMapInfo.StoreMapList) > 1 {
loopStoreTask := tasksch.NewSeqTask("SyncStoresCategory loop stores", ctx.GetUserName(), func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
storeID := loopMapInfo.StoreMapList[step].StoreID
_, err = handler.SyncStoreCategory(ctx, task, storeID, false)
return nil, err
}, len(loopMapInfo.StoreMapList))
loopStoreTask := tasksch.NewSeqTask("SyncStoresCategory loop stores", ctx,
func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
storeID := loopMapInfo.StoreMapList[step].StoreID
_, err = handler.SyncStoreCategory(ctx, task, storeID, false)
return nil, err
}, len(loopMapInfo.StoreMapList))
t.AddChild(loopStoreTask).Run()
_, err = loopStoreTask.GetResult(0)
return nil, err
@@ -342,16 +345,17 @@ func (v *VendorSync) SyncStoresSkus(ctx *jxcontext.Context, db *dao.DaoDB, vendo
loopMapInfo := batchItemList[0].(*LoopStoreMapInfo)
if handler := v.GetStoreHandler(loopMapInfo.VendorID); handler != nil {
if len(loopMapInfo.StoreMapList) > 1 {
loopStoreTask := tasksch.NewSeqTask("SyncStoresSkus相同平台循环门店", ctx.GetUserName(), func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
storeID := loopMapInfo.StoreMapList[step].StoreID
if _, err = handler.SyncStoreSkus(ctx, task, storeID, skuIDs, false, isContinueWhenError); err != nil {
globals.SugarLogger.Debugf("SyncStoresSkus failed1 store:%d failed with error:%v", storeID, err)
if isContinueWhenError {
err = nil
loopStoreTask := tasksch.NewSeqTask("SyncStoresSkus相同平台循环门店", ctx,
func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
storeID := loopMapInfo.StoreMapList[step].StoreID
if _, err = handler.SyncStoreSkus(ctx, task, storeID, skuIDs, false, isContinueWhenError); err != nil {
globals.SugarLogger.Debugf("SyncStoresSkus failed1 store:%d failed with error:%v", storeID, err)
if isContinueWhenError {
err = nil
}
}
}
return nil, err
}, len(loopMapInfo.StoreMapList))
return nil, err
}, len(loopMapInfo.StoreMapList))
t.AddChild(loopStoreTask).Run()
_, err = loopStoreTask.GetResult(0)
return nil, err
@@ -368,11 +372,12 @@ func (v *VendorSync) FullSyncStoresSkus(ctx *jxcontext.Context, db *dao.DaoDB, v
loopMapInfo := batchItemList[0].(*LoopStoreMapInfo)
if handler := v.GetStoreHandler(loopMapInfo.VendorID); handler != nil {
if len(loopMapInfo.StoreMapList) > 1 {
loopStoreTask := tasksch.NewSeqTask("FullSyncStoresSkus相同平台循环门店", ctx.GetUserName(), func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
storeID := loopMapInfo.StoreMapList[step].StoreID
_, err = handler.FullSyncStoreSkus(ctx, task, storeID, false, isContinueWhenError)
return nil, err
}, len(loopMapInfo.StoreMapList))
loopStoreTask := tasksch.NewSeqTask("FullSyncStoresSkus相同平台循环门店", ctx,
func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
storeID := loopMapInfo.StoreMapList[step].StoreID
_, err = handler.FullSyncStoreSkus(ctx, task, storeID, false, isContinueWhenError)
return nil, err
}, len(loopMapInfo.StoreMapList))
t.AddChild(loopStoreTask).Run()
_, err = loopStoreTask.GetResult(0)
return nil, err
@@ -389,11 +394,12 @@ func (v *VendorSync) DeleteRemoteStoreSkus(ctx *jxcontext.Context, db *dao.DaoDB
loopMapInfo := batchItemList[0].(*LoopStoreMapInfo)
if handler := v.GetStoreHandler(loopMapInfo.VendorID); handler != nil {
if len(loopMapInfo.StoreMapList) > 1 {
loopStoreTask := tasksch.NewSeqTask("DeleteRemoteStoreSkus相同平台循环门店", ctx.GetUserName(), func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
storeID := loopMapInfo.StoreMapList[step].StoreID
_, err = handler.DeleteRemoteStoreSkus(ctx, task, storeID, false, isContinueWhenError)
return nil, err
}, len(loopMapInfo.StoreMapList))
loopStoreTask := tasksch.NewSeqTask("DeleteRemoteStoreSkus相同平台循环门店", ctx,
func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
storeID := loopMapInfo.StoreMapList[step].StoreID
_, err = handler.DeleteRemoteStoreSkus(ctx, task, storeID, false, isContinueWhenError)
return nil, err
}, len(loopMapInfo.StoreMapList))
t.AddChild(loopStoreTask).Run()
_, err = loopStoreTask.GetResult(0)
return nil, err
@@ -443,9 +449,8 @@ func (v *VendorSync) LoopStoresMap(ctx *jxcontext.Context, db *dao.DaoDB, taskNa
}
index++
}
task := tasksch.NewParallelTask(taskName, tasksch.NewParallelConfig().SetIsContinueWhenError(true), ctx.GetUserName(), handler, loopInfoList)
ctx.SetTaskOrAddChild(task, nil)
tasksch.ManageTask(task).Run()
task := tasksch.NewParallelTask(taskName, tasksch.NewParallelConfig().SetIsContinueWhenError(true), ctx, handler, loopInfoList)
tasksch.HandleTask(task, nil, true).Run()
if !isAsync {
_, err = task.GetResult(0)
}
@@ -453,62 +458,28 @@ func (v *VendorSync) LoopStoresMap(ctx *jxcontext.Context, db *dao.DaoDB, taskNa
}
func (v *VendorSync) LoopMultiStoresVendors(ctx *jxcontext.Context, db *dao.DaoDB, taskName string, isAsync bool, userName string, handler tasksch.WorkFunc) (hint string, err error) {
task := tasksch.NewParallelTask(taskName, tasksch.NewParallelConfig().SetIsContinueWhenError(true), userName, handler, v.MultiStoreVendorIDs)
ctx.SetTaskOrAddChild(task, nil)
tasksch.ManageTask(task).Run()
task := tasksch.NewParallelTask(taskName, tasksch.NewParallelConfig().SetIsContinueWhenError(true), ctx, handler, v.MultiStoreVendorIDs)
tasksch.HandleTask(task, nil, true).Run()
if !isAsync {
_, err = task.GetResult(0)
}
return task.ID, makeSyncError(err)
}
// func (v *VendorSync) LoopStoreVendors(ctx *jxcontext.Context, db *dao.DaoDB, vendorIDs []int, taskName string, isAsync bool, userName string, handler tasksch.WorkFunc) (hint string, err error) {
// if taskName == "" {
// taskName = "LoopStoreVendors"
// }
// var vendorIDMap map[int]int
// if len(vendorIDs) != 0 {
// vendorIDMap = make(map[int]int)
// for _, v := range vendorIDs {
// vendorIDMap[v] = 1
// }
// }
// allHandlers := make([]int, len(v.MultiStoreVendorIDs)+len(v.SingleStoreVendorIDs))
// copy(allHandlers, v.MultiStoreVendorIDs)
// copy(allHandlers[len(v.MultiStoreVendorIDs):], v.SingleStoreVendorIDs)
// if vendorIDMap != nil {
// count := 0
// for _, v := range allHandlers {
// if vendorIDMap[v] == 1 {
// allHandlers[count] = v
// count++
// }
// }
// allHandlers = allHandlers[:count]
// }
// task := tasksch.NewParallelTask(taskName, nil, userName, handler, allHandlers)
// ctx.SetTaskOrAddChild(task, nil)
// tasksch.ManageTask(task).Run()
// if !isAsync {
// _, err = task.GetResult(0)
// }
// return task.ID, err
// }
func (v *VendorSync) RefreshAllSkusID(ctx *jxcontext.Context, isAsync bool, vendorIDs []int, storeIDs []int) (hint string, err error) {
task := tasksch.NewParallelTask("RefreshAllSkusID", nil, ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
vendorID := batchItemList[0].(int)
if handler := v.GetStoreHandler(vendorID); handler != nil {
if multiHandler, ok := handler.(partner.IMultipleStoresHandler); ok {
_, err = multiHandler.RefreshAllSkusID(ctx, task, false)
} else if singleHandler, ok := handler.(partner.ISingleStoreHandler); ok {
_, err = singleHandler.RefreshStoresAllSkusID(ctx, task, false, storeIDs)
task := tasksch.NewParallelTask("RefreshAllSkusID", nil, ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
vendorID := batchItemList[0].(int)
if handler := v.GetStoreHandler(vendorID); handler != nil {
if multiHandler, ok := handler.(partner.IMultipleStoresHandler); ok {
_, err = multiHandler.RefreshAllSkusID(ctx, task, false)
} else if singleHandler, ok := handler.(partner.ISingleStoreHandler); ok {
_, err = singleHandler.RefreshStoresAllSkusID(ctx, task, false, storeIDs)
}
}
}
return nil, err
}, vendorIDs)
ctx.SetTaskOrAddChild(task, nil)
tasksch.ManageTask(task).Run()
return nil, err
}, vendorIDs)
tasksch.HandleTask(task, nil, true).Run()
if !isAsync {
_, err = task.GetResult(0)
}
@@ -516,15 +487,15 @@ func (v *VendorSync) RefreshAllSkusID(ctx *jxcontext.Context, isAsync bool, vend
}
func (v *VendorSync) RefreshAllStoresID(ctx *jxcontext.Context, isAsync bool, vendorIDs []int) (hint string, err error) {
task := tasksch.NewParallelTask("RefreshAllStoresID", nil, ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
vendorID := batchItemList[0].(int)
if handler := v.GetStoreHandler(vendorID); handler != nil {
_, err = handler.RefreshAllStoresID(ctx, task, false)
}
return nil, err
}, vendorIDs)
ctx.SetTaskOrAddChild(task, nil)
tasksch.ManageTask(task).Run()
task := tasksch.NewParallelTask("RefreshAllStoresID", nil, ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
vendorID := batchItemList[0].(int)
if handler := v.GetStoreHandler(vendorID); handler != nil {
_, err = handler.RefreshAllStoresID(ctx, task, false)
}
return nil, err
}, vendorIDs)
tasksch.HandleTask(task, nil, true).Run()
if !isAsync {
_, err = task.GetResult(0)
}

View File

@@ -100,7 +100,7 @@ func RegisterUser(user *model.User, mobileVerifyCode string, inAuthInfo *auth2.A
func GetUserBindAuthInfo(ctx *jxcontext.Context) (authList []*model.AuthBind, err error) {
authInfo, err := ctx.GetV2AuthInfo()
if err == nil {
return dao.GetUserBindAuthInfo(dao.GetDB(), authInfo.GetID())
return auth2.GetUserBindAuthInfo(authInfo.GetID())
}
return nil, err
}

View File

@@ -52,51 +52,51 @@ func SendFilesToStores(ctx *jxcontext.Context, files []*multipart.FileHeader, ti
}
upToken := putPolicy.UploadToken(api.QiniuAPI)
cfg := &storage.Config{}
task := tasksch.NewParallelTask("SendFilesToStores", tasksch.NewParallelConfig().SetIsContinueWhenError(true), userName, func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
fileInfo := batchItemList[0].(*tUploadFileInfo)
fileHeader := fileInfo.FileHeader
storeID := fileInfo.StoreID
file, err := fileHeader.Open()
globals.SugarLogger.Debugf("SendFilesToStores upload file:%s", fileHeader.Filename)
if err == nil {
ret := storage.PutRet{}
key := "storeBill_" + utils.Int2Str(storeID) + "_" + strings.ToLower(utils.GetUUID()) + path.Ext(fileHeader.Filename)
formUploader := storage.NewFormUploader(cfg)
for i := 0; i < 3; i++ {
if err = formUploader.Put(context.Background(), &ret, upToken, key, file, fileHeader.Size, nil); err == nil {
break
}
}
file.Close()
task := tasksch.NewParallelTask("SendFilesToStores", tasksch.NewParallelConfig().SetIsContinueWhenError(true), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
fileInfo := batchItemList[0].(*tUploadFileInfo)
fileHeader := fileInfo.FileHeader
storeID := fileInfo.StoreID
file, err := fileHeader.Open()
globals.SugarLogger.Debugf("SendFilesToStores upload file:%s", fileHeader.Filename)
if err == nil {
db := dao.GetDB()
billRec := &legacymodel.StoreBill{
Date: time.Now(),
Url: jxutils.ComposeQiniuResURL(ret.Key),
StoreId: storeID,
BillName: fileHeader.Filename,
ShopName: shopName,
BillTitle: title,
}
if err = dao.CreateEntity(db, billRec); err == nil {
err = weixinmsg.NotifySaleBill(storeID, title, shopName, "http://www.jxc4.com/billshow/?path="+billRec.Url)
if err != nil {
globals.SugarLogger.Infof("SendFilesToStores NotifySaleBill file:%s error:%v", fileHeader.Filename, err)
ret := storage.PutRet{}
key := "storeBill_" + utils.Int2Str(storeID) + "_" + strings.ToLower(utils.GetUUID()) + path.Ext(fileHeader.Filename)
formUploader := storage.NewFormUploader(cfg)
for i := 0; i < 3; i++ {
if err = formUploader.Put(context.Background(), &ret, upToken, key, file, fileHeader.Size, nil); err == nil {
break
}
}
file.Close()
if err == nil {
db := dao.GetDB()
billRec := &legacymodel.StoreBill{
Date: time.Now(),
Url: jxutils.ComposeQiniuResURL(ret.Key),
StoreId: storeID,
BillName: fileHeader.Filename,
ShopName: shopName,
BillTitle: title,
}
if err = dao.CreateEntity(db, billRec); err == nil {
err = weixinmsg.NotifySaleBill(storeID, title, shopName, "http://www.jxc4.com/billshow/?path="+billRec.Url)
if err != nil {
globals.SugarLogger.Infof("SendFilesToStores NotifySaleBill file:%s error:%v", fileHeader.Filename, err)
}
err = nil // 忽略微信发送错误
} else {
globals.SugarLogger.Warnf("SendFilesToStores CreateEntity file:%s error:%v", fileHeader.Filename, err)
}
err = nil // 忽略微信发送错误
} else {
globals.SugarLogger.Warnf("SendFilesToStores CreateEntity file:%s error:%v", fileHeader.Filename, err)
globals.SugarLogger.Warnf("SendFilesToStores file:%s failed with error:%v", fileHeader.Filename, err)
}
} else {
globals.SugarLogger.Warnf("SendFilesToStores file:%s failed with error:%v", fileHeader.Filename, err)
globals.SugarLogger.Warnf("SendFilesToStores open file:%s failed with error:%v", fileHeader.Filename, err)
}
} else {
globals.SugarLogger.Warnf("SendFilesToStores open file:%s failed with error:%v", fileHeader.Filename, err)
}
return retVal, err
}, fileList)
ctx.SetTaskOrAddChild(task, nil)
tasksch.ManageTask(task).Run()
return retVal, err
}, fileList)
tasksch.HandleTask(task, nil, true).Run()
hint = task.ID
if !isAsync {
_, err = task.GetResult(0)

View File

@@ -147,22 +147,23 @@ func InitSkuName(ctx *jxcontext.Context, isForce, isAsync, isContinueWhenError b
return "", err
}
task := tasksch.NewParallelTask("InitSkuName calculate md5", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
skuName := batchItemList[0].(*model.SkuName)
if skuName.ImgHashCode == "" || isForce {
response, err := http.Get(skuName.Img)
if err == nil {
defer response.Body.Close()
data, err2 := ioutil.ReadAll(response.Body)
if err = err2; err == nil {
skuName.ImgHashCode = fmt.Sprintf("%X", md5.Sum(data))
db := dao.GetDB()
_, err = dao.UpdateEntity(db, skuName, "ImgHashCode")
task := tasksch.NewParallelTask("InitSkuName calculate md5", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
skuName := batchItemList[0].(*model.SkuName)
if skuName.ImgHashCode == "" || isForce {
response, err := http.Get(skuName.Img)
if err == nil {
defer response.Body.Close()
data, err2 := ioutil.ReadAll(response.Body)
if err = err2; err == nil {
skuName.ImgHashCode = fmt.Sprintf("%X", md5.Sum(data))
db := dao.GetDB()
_, err = dao.UpdateEntity(db, skuName, "ImgHashCode")
}
}
}
}
return nil, err
}, skuNameList)
return nil, err
}, skuNameList)
tasksch.ManageTask(task).Run()
if !isAsync {
_, err = task.GetResult(0)
@@ -207,17 +208,18 @@ func UploadWeimobImg4SkuName(ctx *jxcontext.Context, nameIDs []int, isAsync, isC
if err != nil {
return "", err
}
rootTask := tasksch.NewParallelTask("UploadWeimobImg4SkuName", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError).SetParallelCount(5), ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
skuName := batchItemList[0].(*model.SkuName)
if skuName.Img != "" && skuName.ImgWeimob == "" {
if globals.EnableWscStoreWrite {
if skuName.ImgWeimob, err = api.WeimobAPI.UploadImgByURL(skuName.Img, ""); err == nil {
_, err = dao.UpdateEntity(db, skuName, "ImgWeimob")
rootTask := tasksch.NewParallelTask("UploadWeimobImg4SkuName", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError).SetParallelCount(5), ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
skuName := batchItemList[0].(*model.SkuName)
if skuName.Img != "" && skuName.ImgWeimob == "" {
if globals.EnableWscStoreWrite {
if skuName.ImgWeimob, err = api.WeimobAPI.UploadImgByURL(skuName.Img, ""); err == nil {
_, err = dao.UpdateEntity(db, skuName, "ImgWeimob")
}
}
}
}
return nil, err
}, skuNameList)
return nil, err
}, skuNameList)
tasksch.ManageTask(rootTask).Run()
if !isAsync {
@@ -350,76 +352,77 @@ func BuildSkuFromEbaiStore(ctx *jxcontext.Context, baiduShopID int64, isAsync, i
}
cfg := &storage.Config{}
upToken := putPolicy.UploadToken(api.QiniuAPI)
rootTask := tasksch.NewSeqTask("BuildSkuFromEbaiStore", ctx.GetUserName(), func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
var catID string
cat := skuCatList[step]
skuNameExtList := allSkuInfo2[cat]
catID, err = addShopCategory(0, cat.Name, int(cat.Level), cat.Seq, ctx.GetUserName())
if err == nil {
shopCategories := []int64{utils.Str2Int64(catID)}
for _, skuNameExt := range skuNameExtList {
var imgContent []byte
skuNameExt.CategoryID = cat.ID
skuNameExt.Img = strings.Replace(skuNameExt.Img, "https://", "http://", 1)
if imgContent, _, err = jxutils.DownloadFileByURL(skuNameExt.Img); err != nil {
globals.SugarLogger.Infof("download pic %s failed with error:%v", skuNameExt.Img, err)
if !isContinueWhenError {
return nil, err
}
err = nil
continue
}
formUploader := storage.NewFormUploader(cfg)
ret := storage.PutRet{}
key := jxutils.GenPicFileName(".jpeg")
for i := 0; i < 3; i++ {
if err = formUploader.Put(context.Background(), &ret, upToken, key, bytes.NewReader(imgContent), int64(len(imgContent)), nil); err == nil {
break
}
}
if err != nil {
globals.SugarLogger.Infof("upload pic %s failed with error:%v", skuNameExt.Img, err)
if !isContinueWhenError {
return nil, err
}
err = nil
continue
}
qiniuImgURL := "http://image.jxc4.com/" + key + "?imageMogr2/thumbnail/x800/gravity/Center/crop/800x800"
for _, sku := range skuNameExt.Skus {
jdCatID := 22410 // 其他国产水果
if cat.Name == "进口水果" {
jdCatID = 20342 // 其他进口水果
}
price := sku.LinkID
sku.LinkID = 0
skuName := jxutils.ComposeSkuName(skuNameExt.Prefix, skuNameExt.Name, sku.Comment, skuNameExt.Unit, sku.SpecQuality, sku.SpecUnit, jdapi.MaxSkuNameLen)
fixedStatus := 1
if sku.Status != model.SkuStatusNormal {
fixedStatus = 2
}
var vendorSkuID string
vendorSkuID, err = addSku(utils.Int2Str(startOutSkuID), jdCatID, shopCategories, jd.DefBrandID, skuName, price, jxutils.IntWeight2Float(sku.Weight), []string{qiniuImgURL}, fixedStatus, true, nil)
if err == nil {
globals.SugarLogger.Debugf("vendorSkuID=%s", vendorSkuID)
} else {
globals.SugarLogger.Infof("create %s failed with error:%v", skuName, err)
rootTask := tasksch.NewSeqTask("BuildSkuFromEbaiStore", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
var catID string
cat := skuCatList[step]
skuNameExtList := allSkuInfo2[cat]
catID, err = addShopCategory(0, cat.Name, int(cat.Level), cat.Seq, ctx.GetUserName())
if err == nil {
shopCategories := []int64{utils.Str2Int64(catID)}
for _, skuNameExt := range skuNameExtList {
var imgContent []byte
skuNameExt.CategoryID = cat.ID
skuNameExt.Img = strings.Replace(skuNameExt.Img, "https://", "http://", 1)
if imgContent, _, err = jxutils.DownloadFileByURL(skuNameExt.Img); err != nil {
globals.SugarLogger.Infof("download pic %s failed with error:%v", skuNameExt.Img, err)
if !isContinueWhenError {
return nil, err
}
err = nil
continue
}
formUploader := storage.NewFormUploader(cfg)
ret := storage.PutRet{}
key := jxutils.GenPicFileName(".jpeg")
for i := 0; i < 3; i++ {
if err = formUploader.Put(context.Background(), &ret, upToken, key, bytes.NewReader(imgContent), int64(len(imgContent)), nil); err == nil {
break
}
}
if err != nil {
globals.SugarLogger.Infof("upload pic %s failed with error:%v", skuNameExt.Img, err)
if !isContinueWhenError {
return nil, err
}
err = nil
continue
}
qiniuImgURL := "http://image.jxc4.com/" + key + "?imageMogr2/thumbnail/x800/gravity/Center/crop/800x800"
for _, sku := range skuNameExt.Skus {
jdCatID := 22410 // 其他国产水果
if cat.Name == "进口水果" {
jdCatID = 20342 // 其他进口水果
}
price := sku.LinkID
sku.LinkID = 0
skuName := jxutils.ComposeSkuName(skuNameExt.Prefix, skuNameExt.Name, sku.Comment, skuNameExt.Unit, sku.SpecQuality, sku.SpecUnit, jdapi.MaxSkuNameLen)
fixedStatus := 1
if sku.Status != model.SkuStatusNormal {
fixedStatus = 2
}
var vendorSkuID string
vendorSkuID, err = addSku(utils.Int2Str(startOutSkuID), jdCatID, shopCategories, jd.DefBrandID, skuName, price, jxutils.IntWeight2Float(sku.Weight), []string{qiniuImgURL}, fixedStatus, true, nil)
if err == nil {
globals.SugarLogger.Debugf("vendorSkuID=%s", vendorSkuID)
} else {
globals.SugarLogger.Infof("create %s failed with error:%v", skuName, err)
if !isContinueWhenError {
return nil, err
}
err = nil
}
// fmt.Printf("%s,[%s]%s-%f-%s, %s, %s\n", cat.Name, skuNameExt.Prefix, skuNameExt.Name, skuNameExt.SpecQuality, skuNameExt.SpecUnit, qiniuImgURL, skuName)
startOutSkuID++
// rootTask.Cancel()
// return nil, nil
}
// fmt.Printf("%s,[%s]%s-%f-%s, %s, %s\n", cat.Name, skuNameExt.Prefix, skuNameExt.Name, skuNameExt.SpecQuality, skuNameExt.SpecUnit, qiniuImgURL, skuName)
startOutSkuID++
// rootTask.Cancel()
// return nil, nil
}
} else {
return nil, err
}
} else {
return nil, err
}
return nil, err
}, len(skuCatList))
}, len(skuCatList))
tasksch.ManageTask(rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)

View File

@@ -424,64 +424,66 @@ func CreateJdPromotion(ctx *jxcontext.Context, isIDJd bool, isAsync, isContinueW
}
dao.Commit(db)
rootTask := tasksch.NewSeqTask("CreateJdPromotion", userName, func(task *tasksch.SeqTask, step int, params2 ...interface{}) (result interface{}, err error) {
if step == 0 {
task1 := tasksch.NewParallelTask("CreateJdPromotion update sku price", nil, userName, func(t *tasksch.ParallelTask, batchItemList []interface{}, params2 ...interface{}) (retVal interface{}, err error) {
storeID := batchItemList[0].(int)
modifyPricesList := jxutils.SplitSlice(modifyPricesList[storeID], jdapi.MaxStoreSkuBatchSize)
for _, modifyPrices := range modifyPricesList {
modifyPrices2 := make([]*jdapi.SkuPriceInfo, len(modifyPrices))
for k, v := range modifyPrices {
modifyPrices2[k] = v.(*jdapi.SkuPriceInfo)
}
if globals.EnableStoreWrite {
if _, err = api.JdAPI.UpdateVendorStationPrice(utils.Int2Str(storeID), "", modifyPrices2); err != nil {
return nil, err
rootTask := tasksch.NewSeqTask("CreateJdPromotion", ctx,
func(task *tasksch.SeqTask, step int, params2 ...interface{}) (result interface{}, err error) {
if step == 0 {
task1 := tasksch.NewParallelTask("CreateJdPromotion update sku price", nil, ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params2 ...interface{}) (retVal interface{}, err error) {
storeID := batchItemList[0].(int)
modifyPricesList := jxutils.SplitSlice(modifyPricesList[storeID], jdapi.MaxStoreSkuBatchSize)
for _, modifyPrices := range modifyPricesList {
modifyPrices2 := make([]*jdapi.SkuPriceInfo, len(modifyPrices))
for k, v := range modifyPrices {
modifyPrices2[k] = v.(*jdapi.SkuPriceInfo)
}
if globals.EnableStoreWrite {
if _, err = api.JdAPI.UpdateVendorStationPrice(utils.Int2Str(storeID), "", modifyPrices2); err != nil {
return nil, err
}
}
}
return nil, nil
}, jxStoreIDs)
task.AddChild(task1).Run()
_, err = task1.GetResult(0)
} else if step == 1 {
err = promotionHandler.CreatePromotionRules(infoId, "", limitDevice, limitPin, limitCount, limitDaily)
} else if step == 2 {
task2 := tasksch.NewParallelTask("CreateJdPromotion CreatePromotionSku", tasksch.NewParallelConfig().SetBatchSize(MaxPromotionSkuCount).SetIsContinueWhenError(isContinueWhenError), ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params2 ...interface{}) (retVal interface{}, err error) {
skus := make([]map[string]interface{}, len(batchItemList))
for k, v := range batchItemList {
skus[k] = v.(map[string]interface{})
}
_, err = promotionHandler.CreatePromotionSku(infoId, "", skus)
return nil, err
}, promotionPrices)
task.AddChild(task2).Run()
_, err = task2.GetResult(0)
if isContinueWhenError && err != nil { // todo isContinueWhenError为true时强制忽略此步的错误
err = nil
}
} else if step == 3 {
err = promotionHandler.ConfirmPromotion(infoId, "")
if err == nil {
db := dao.GetDB()
if _, err = dao.UpdateEntityLogically(db, promotion, map[string]interface{}{
model.FieldStatus: model.PromotionStatusRemoteCreated,
}, ctx.GetUserName(), nil); err == nil {
RefreshJdPromotionLockStatus(ctx, promotion.ID)
}
}
return nil, nil
}, jxStoreIDs)
task.AddChild(task1).Run()
_, err = task1.GetResult(0)
} else if step == 1 {
err = promotionHandler.CreatePromotionRules(infoId, "", limitDevice, limitPin, limitCount, limitDaily)
} else if step == 2 {
task2 := tasksch.NewParallelTask("CreateJdPromotion CreatePromotionSku", tasksch.NewParallelConfig().SetBatchSize(MaxPromotionSkuCount).SetIsContinueWhenError(isContinueWhenError), userName, func(task *tasksch.ParallelTask, batchItemList []interface{}, params2 ...interface{}) (retVal interface{}, err error) {
skus := make([]map[string]interface{}, len(batchItemList))
for k, v := range batchItemList {
skus[k] = v.(map[string]interface{})
}
_, err = promotionHandler.CreatePromotionSku(infoId, "", skus)
return nil, err
}, promotionPrices)
task.AddChild(task2).Run()
_, err = task2.GetResult(0)
if isContinueWhenError && err != nil { // todo isContinueWhenError为true时强制忽略此步的错误
err = nil
}
} else if step == 3 {
err = promotionHandler.ConfirmPromotion(infoId, "")
if err == nil {
if err != nil {
db := dao.GetDB()
if _, err = dao.UpdateEntityLogically(db, promotion, map[string]interface{}{
model.FieldStatus: model.PromotionStatusRemoteCreated,
}, ctx.GetUserName(), nil); err == nil {
RefreshJdPromotionLockStatus(ctx, promotion.ID)
}
dao.UpdateEntityLogically(db, promotion, map[string]interface{}{
model.FieldStatus: model.PromotionStatusRemoteFailed,
model.FieldRemark: err.Error(),
}, ctx.GetUserName(), nil)
}
}
if err != nil {
db := dao.GetDB()
dao.UpdateEntityLogically(db, promotion, map[string]interface{}{
model.FieldStatus: model.PromotionStatusRemoteFailed,
model.FieldRemark: err.Error(),
}, ctx.GetUserName(), nil)
}
return nil, err
}, 4)
ctx.SetTaskOrAddChild(rootTask, nil)
tasksch.ManageTask(rootTask).Run()
return nil, err
}, 4)
tasksch.HandleTask(rootTask, nil, true).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
}
@@ -745,32 +747,33 @@ func RefreshJdStoreSkuStock(promotionID int, skuIDs []int) (err error) {
}
globals.SugarLogger.Debugf("RefreshJdStoreSkuStock promotionID:%d, len(promotionItemList)=%d", promotionID, len(promotionItemList))
if len(promotionItemList) > 0 {
task := tasksch.NewParallelTask("RefreshJdStoreSkuStock", tasksch.NewParallelConfig().SetBatchSize(jdapi.MaxStoreSkuBatchSize).SetIsContinueWhenError(true), "schedule", func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
stockList := make([]*jdapi.SkuStock, 0)
stationNo := batchItemList[0].(*tPromotionItemInfo).JdStoreID
for _, v := range batchItemList {
promotionItem := v.(*tPromotionItemInfo)
if promotionItem.JdStoreID != stationNo {
// globals.SugarLogger.Debugf("RefreshJdStoreSkuStock BatchUpdateCurrentQtys stationNo:%s, stockList:%s", stationNo, utils.Format4Output(stockList, false))
_, err = api.JdAPI.BatchUpdateCurrentQtys("", stationNo, stockList, userName)
if err != nil {
globals.SugarLogger.Warnf("RefreshJdStoreSkuStock BatchUpdateCurrentQtys failed with error:%v", err)
task := tasksch.NewParallelTask("RefreshJdStoreSkuStock", tasksch.NewParallelConfig().SetBatchSize(jdapi.MaxStoreSkuBatchSize).SetIsContinueWhenError(true), jxcontext.AdminCtx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
stockList := make([]*jdapi.SkuStock, 0)
stationNo := batchItemList[0].(*tPromotionItemInfo).JdStoreID
for _, v := range batchItemList {
promotionItem := v.(*tPromotionItemInfo)
if promotionItem.JdStoreID != stationNo {
// globals.SugarLogger.Debugf("RefreshJdStoreSkuStock BatchUpdateCurrentQtys stationNo:%s, stockList:%s", stationNo, utils.Format4Output(stockList, false))
_, err = api.JdAPI.BatchUpdateCurrentQtys("", stationNo, stockList, userName)
if err != nil {
globals.SugarLogger.Warnf("RefreshJdStoreSkuStock BatchUpdateCurrentQtys failed with error:%v", err)
}
stockList = make([]*jdapi.SkuStock, 0)
stationNo = promotionItem.JdStoreID
}
stockList = make([]*jdapi.SkuStock, 0)
stationNo = promotionItem.JdStoreID
stockList = append(stockList, &jdapi.SkuStock{
OutSkuId: utils.Int2Str(promotionItem.SkuID),
StockQty: model.MaxStoreSkuStockQty,
})
}
stockList = append(stockList, &jdapi.SkuStock{
OutSkuId: utils.Int2Str(promotionItem.SkuID),
StockQty: model.MaxStoreSkuStockQty,
})
}
// globals.SugarLogger.Debugf("RefreshJdStoreSkuStock BatchUpdateCurrentQtys stationNo:%s, stockList:%s", stationNo, utils.Format4Output(stockList, false))
_, err = api.JdAPI.BatchUpdateCurrentQtys("", stationNo, stockList, userName)
if err != nil {
globals.SugarLogger.Warnf("RefreshJdStoreSkuStock BatchUpdateCurrentQtys failed with error:%v", err)
}
return nil, err
}, promotionItemList)
// globals.SugarLogger.Debugf("RefreshJdStoreSkuStock BatchUpdateCurrentQtys stationNo:%s, stockList:%s", stationNo, utils.Format4Output(stockList, false))
_, err = api.JdAPI.BatchUpdateCurrentQtys("", stationNo, stockList, userName)
if err != nil {
globals.SugarLogger.Warnf("RefreshJdStoreSkuStock BatchUpdateCurrentQtys failed with error:%v", err)
}
return nil, err
}, promotionItemList)
task.Run()
_, err = task.GetResult(0)
}

View File

@@ -65,22 +65,22 @@ func SendAdvertingByGoodsOrder(ctx *jxcontext.Context, advertising string, days
mobileNumbers = append(mobileNumbers, "18180948107")
smsClient := aliyunsmsclient.New("http://dysmsapi.aliyuncs.com/")
task := tasksch.NewParallelTask("SendAdvertingByGoodsOrder", tasksch.NewParallelConfig().SetBatchSize(MaxBatchSize), userName, func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
numbers := make([]string, len(batchItemList))
for k, v := range batchItemList {
numbers[k] = v.(string)
}
numberStr := strings.Join(numbers, ",")
_, err = smsClient.Execute(globals.AliKey, globals.AliSecret, numberStr, "京西菜市", "SMS_109345355", string(utils.MustMarshal(map[string]interface{}{
"code": "code",
})))
if err != nil {
globals.SugarLogger.Infof("SendAdvertingByGoodsOrder numbers:%s failed with error:%v", numberStr, err)
}
return nil, err
}, mobileNumbers)
ctx.SetTaskOrAddChild(task, nil)
tasksch.ManageTask(task).Run()
task := tasksch.NewParallelTask("SendAdvertingByGoodsOrder", tasksch.NewParallelConfig().SetBatchSize(MaxBatchSize), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
numbers := make([]string, len(batchItemList))
for k, v := range batchItemList {
numbers[k] = v.(string)
}
numberStr := strings.Join(numbers, ",")
_, err = smsClient.Execute(globals.AliKey, globals.AliSecret, numberStr, "京西菜市", "SMS_109345355", string(utils.MustMarshal(map[string]interface{}{
"code": "code",
})))
if err != nil {
globals.SugarLogger.Infof("SendAdvertingByGoodsOrder numbers:%s failed with error:%v", numberStr, err)
}
return nil, err
}, mobileNumbers)
tasksch.HandleTask(task, nil, true).Run()
if !isAsync {
_, err = task.GetResult(0)

View File

@@ -138,11 +138,12 @@ func Convert2JDSPU(ctx *jxcontext.Context, count int, isAsync, isContinueWhenErr
if err = dao.GetRows(db, &skuNameList, sql, utils.DefaultTimeValue); err != nil {
return "", err
}
rootTask := tasksch.NewParallelTask("Convert2JDSPU", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
skuName := batchItemList[0].(*model.SkuName)
_, err = cms.CurVendorSync.SyncSku(ctx, db, skuName.ID, -1, false, isContinueWhenError, ctx.GetUserName())
return nil, err
}, skuNameList)
rootTask := tasksch.NewParallelTask("Convert2JDSPU", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
skuName := batchItemList[0].(*model.SkuName)
_, err = cms.CurVendorSync.SyncSku(ctx, db, skuName.ID, -1, false, isContinueWhenError, ctx.GetUserName())
return nil, err
}, skuNameList)
tasksch.ManageTask(rootTask).Run()
if !isAsync {
@@ -283,8 +284,9 @@ func Change2JDSPU4Store(ctx *jxcontext.Context, storeIDs []int, step int, isAsyn
func TransferLegacyJdOrder(ctx *jxcontext.Context, isAsync, isContinueWhenError bool) (hint string, err error) {
sqlBatchCount := 1000
rootTask := tasksch.NewSeqTask("TransferLegacyJdOrder", ctx.GetUserName(), func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
sql := `
rootTask := tasksch.NewSeqTask("TransferLegacyJdOrder", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
sql := `
SELECT t1.*
FROM jdorder t1
LEFT JOIN goods_order_original t2 ON t2.vendor_order_id = t1.vendor_order_id
@@ -292,58 +294,59 @@ func TransferLegacyJdOrder(ctx *jxcontext.Context, isAsync, isContinueWhenError
ORDER BY t1.orderstatustime
LIMIT ?
`
db := dao.GetDB()
var jdOrderList []*legacymodel2.Jdorder
if err = dao.GetRows(db, &jdOrderList, sql, sqlBatchCount); err != nil {
return nil, err
}
if len(jdOrderList) > 0 {
task := tasksch.NewParallelTask("TransferLegacyJdOrder2", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError).SetBatchSize(40), ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
var orderDetailList []*model.GoodsOrderOriginal
for _, v := range batchItemList {
jdOrder := v.(*legacymodel2.Jdorder)
var detail map[string]interface{}
if err = utils.UnmarshalUseNumber([]byte(strings.Replace(strings.Replace(jdOrder.Data, "\n", "", -1), "\r", "", -1)), &detail); err != nil {
return nil, err
}
resultList := detail["result"].(map[string]interface{})["resultList"].([]interface{})
if len(resultList) > 0 {
originalData := resultList[0].(map[string]interface{})
orgCode := originalData["orgCode"].(string)
if orgCode == "320406" {
orderPurchaseTime := utils.Interface2String(originalData["orderPurchaseTime"])
if orderPurchaseTime == "" {
globals.SugarLogger.Debugf("TransferLegacyJdOrder abnormal order:%s", jdOrder.VendorOrderID)
orderPurchaseTime = utils.Interface2String(originalData["orderStartTime"])
db := dao.GetDB()
var jdOrderList []*legacymodel2.Jdorder
if err = dao.GetRows(db, &jdOrderList, sql, sqlBatchCount); err != nil {
return nil, err
}
if len(jdOrderList) > 0 {
task := tasksch.NewParallelTask("TransferLegacyJdOrder2", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError).SetBatchSize(40), ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
var orderDetailList []*model.GoodsOrderOriginal
for _, v := range batchItemList {
jdOrder := v.(*legacymodel2.Jdorder)
var detail map[string]interface{}
if err = utils.UnmarshalUseNumber([]byte(strings.Replace(strings.Replace(jdOrder.Data, "\n", "", -1), "\r", "", -1)), &detail); err != nil {
return nil, err
}
if orderPurchaseTime != "" {
orderDetail := &model.GoodsOrderOriginal{
VendorOrderID: jdOrder.VendorOrderID,
VendorID: model.VendorIDJD,
AccountNo: orgCode,
OrderCreatedAt: utils.Str2Time(orderPurchaseTime),
OriginalData: string(utils.MustMarshal(originalData)),
resultList := detail["result"].(map[string]interface{})["resultList"].([]interface{})
if len(resultList) > 0 {
originalData := resultList[0].(map[string]interface{})
orgCode := originalData["orgCode"].(string)
if orgCode == "320406" {
orderPurchaseTime := utils.Interface2String(originalData["orderPurchaseTime"])
if orderPurchaseTime == "" {
globals.SugarLogger.Debugf("TransferLegacyJdOrder abnormal order:%s", jdOrder.VendorOrderID)
orderPurchaseTime = utils.Interface2String(originalData["orderStartTime"])
}
if orderPurchaseTime != "" {
orderDetail := &model.GoodsOrderOriginal{
VendorOrderID: jdOrder.VendorOrderID,
VendorID: model.VendorIDJD,
AccountNo: orgCode,
OrderCreatedAt: utils.Str2Time(orderPurchaseTime),
OriginalData: string(utils.MustMarshal(originalData)),
}
orderDetailList = append(orderDetailList, orderDetail)
} else {
globals.SugarLogger.Debugf("TransferLegacyJdOrder abnormal2 order:%s", jdOrder.VendorOrderID)
}
}
orderDetailList = append(orderDetailList, orderDetail)
} else {
globals.SugarLogger.Debugf("TransferLegacyJdOrder abnormal2 order:%s", jdOrder.VendorOrderID)
}
}
}
}
if len(orderDetailList) > 0 {
err = dao.CreateMultiEntities(db, orderDetailList)
}
return nil, err
}, jdOrderList)
// rootTask.AddChild(task).Run()
task.Run()
_, err = task.GetResult(0)
} else {
rootTask.Cancel()
}
return nil, err
}, math.MaxInt32)
if len(orderDetailList) > 0 {
err = dao.CreateMultiEntities(db, orderDetailList)
}
return nil, err
}, jdOrderList)
// rootTask.AddChild(task).Run()
task.Run()
_, err = task.GetResult(0)
} else {
rootTask.Cancel()
}
return nil, err
}, math.MaxInt32)
tasksch.ManageTask(rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
@@ -484,38 +487,39 @@ func PullJdOrder(ctx *jxcontext.Context, fromTime, toTime time.Time, isAsync, is
gapList[k] = k
}
rootTask := tasksch.NewParallelTask("PullJdOrder", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError).SetParallelCount(20), ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
gapIndex := batchItemList[0].(int)
hourIndex := gapIndex * hourGap
subFromTime := fromTime.Add(time.Duration(hourIndex) * time.Hour)
subToTime := fromTime.Add(time.Duration(hourIndex+hourGap) * time.Hour)
if subToTime.Sub(toTime) > 0 {
subToTime = toTime
}
if true { //gapIndex < gapCount-1 {
subToTime = subToTime.Add(-1 * time.Second) // 减一秒
}
commonParams := map[string]interface{}{
jdapi.KeyPageSize: pageSize,
"orderPurchaseTime_begin": utils.Time2Str(subFromTime),
"orderPurchaseTime_end": utils.Time2Str(subToTime),
}
// globals.SugarLogger.Debugf("PullJdOrder, commonParams=%s", utils.Format4Output(commonParams, false))
orderList, totalCount, err := api.JdAPI.OrderQuery(commonParams)
if err != nil {
return "", err
}
storeOrderList, err := api.JdAPI.GetStoreOrderInfoList(utils.Time2Str(subFromTime), utils.Time2Str(subToTime))
if err != nil {
}
if err = saveJdOrderList(existJdIDMap, orderList, storeOrderList); err != nil {
return "", err
}
if false {
globals.SugarLogger.Debugf("subFromTime:%s, subToTime:%s, totalCount:%d, len(orderList):%d", utils.Time2Str(subFromTime), utils.Time2Str(subToTime), totalCount, len(orderList))
}
return nil, err
}, gapList)
rootTask := tasksch.NewParallelTask("PullJdOrder", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError).SetParallelCount(20), ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
gapIndex := batchItemList[0].(int)
hourIndex := gapIndex * hourGap
subFromTime := fromTime.Add(time.Duration(hourIndex) * time.Hour)
subToTime := fromTime.Add(time.Duration(hourIndex+hourGap) * time.Hour)
if subToTime.Sub(toTime) > 0 {
subToTime = toTime
}
if true { //gapIndex < gapCount-1 {
subToTime = subToTime.Add(-1 * time.Second) // 减一秒
}
commonParams := map[string]interface{}{
jdapi.KeyPageSize: pageSize,
"orderPurchaseTime_begin": utils.Time2Str(subFromTime),
"orderPurchaseTime_end": utils.Time2Str(subToTime),
}
// globals.SugarLogger.Debugf("PullJdOrder, commonParams=%s", utils.Format4Output(commonParams, false))
orderList, totalCount, err := api.JdAPI.OrderQuery(commonParams)
if err != nil {
return "", err
}
storeOrderList, err := api.JdAPI.GetStoreOrderInfoList(utils.Time2Str(subFromTime), utils.Time2Str(subToTime))
if err != nil {
}
if err = saveJdOrderList(existJdIDMap, orderList, storeOrderList); err != nil {
return "", err
}
if false {
globals.SugarLogger.Debugf("subFromTime:%s, subToTime:%s, totalCount:%d, len(orderList):%d", utils.Time2Str(subFromTime), utils.Time2Str(subToTime), totalCount, len(orderList))
}
return nil, err
}, gapList)
tasksch.ManageTask(rootTask).Run()
if !isAsync {
@@ -562,17 +566,18 @@ func DeleteWrongSpu(ctx *jxcontext.Context, isAsync, isContinueWhenError bool) (
if err = dao.GetRows(db, &skuNameList, sql, utils.DefaultTimeValue); err != nil {
return "", err
}
rootTask := tasksch.NewSeqTask("DeleteWrongSpu", ctx.GetUserName(), func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
mapData := map[string]interface{}{
"name": skuNameList[step].Name,
}
_, err = cms.UpdateSkuName(ctx, skuNameList[step].ID, mapData, ctx.GetUserName())
if err != nil {
globals.SugarLogger.Debugf("DeleteWrongSpu failed nameid:%d, name:%s, with error:%v", skuNameList[step].ID, skuNameList[step].Name, err)
err = nil // 强制忽略错误
}
return nil, err
}, len(skuNameList))
rootTask := tasksch.NewSeqTask("DeleteWrongSpu", ctx,
func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
mapData := map[string]interface{}{
"name": skuNameList[step].Name,
}
_, err = cms.UpdateSkuName(ctx, skuNameList[step].ID, mapData, ctx.GetUserName())
if err != nil {
globals.SugarLogger.Debugf("DeleteWrongSpu failed nameid:%d, name:%s, with error:%v", skuNameList[step].ID, skuNameList[step].Name, err)
err = nil // 强制忽略错误
}
return nil, err
}, len(skuNameList))
tasksch.ManageTask(rootTask).Run()
if !isAsync {
@@ -590,8 +595,9 @@ type GoodsOrderOriginalEx struct {
func CreateOrderFromOriginal(ctx *jxcontext.Context, isAsync, isContinueWhenError bool) (hint string, err error) {
sqlBatchCount := 5000
rootTask := tasksch.NewSeqTask("CreateOrderFromOriginal", ctx.GetUserName(), func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
sql := `
rootTask := tasksch.NewSeqTask("CreateOrderFromOriginal", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
sql := `
SELECT t1.*, t3.order_status
FROM goods_order_original t1
LEFT JOIN goods_order t2 ON t2.vendor_order_id = t1.vendor_order_id
@@ -599,58 +605,59 @@ func CreateOrderFromOriginal(ctx *jxcontext.Context, isAsync, isContinueWhenErro
WHERE t2.id IS NULL
LIMIT ?;
`
rawDB := orm.NewOrm()
db := dao.WrapDB(rawDB)
var orderList []*GoodsOrderOriginalEx
if err = dao.GetRows(db, &orderList, sql, sqlBatchCount); err != nil {
return nil, err
}
if len(orderList) > 0 {
task := tasksch.NewParallelTask("CreateOrderFromOriginal", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError).SetParallelCount(1), ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
orderOriginal := batchItemList[0].(*GoodsOrderOriginalEx)
globals.SugarLogger.Debugf("CreateOrderFromOriginal processing orderID:%s", orderOriginal.VendorOrderID)
if handler := partner.GetPurchasePlatformFromVendorID(orderOriginal.VendorID); handler != nil {
var detail map[string]interface{}
if err = utils.UnmarshalUseNumber([]byte(strings.Replace(strings.Replace(orderOriginal.OriginalData, "\n", "", -1), "\r", "", -1)), &detail); err != nil {
globals.SugarLogger.Debugf("CreateOrderFromOriginal abnormal orderID:%s, error:%v", orderOriginal.VendorOrderID, err)
return nil, err
}
order := handler.Map2Order(detail)
if order.Status < model.OrderStatusEndBegin {
if orderOriginal.OrderStatus == 3 {
order.Status = model.OrderStatusFinished
} else if orderOriginal.OrderStatus == 7 {
order.Status = model.OrderStatusCanceled
} else {
order2, err2 := handler.GetOrder(order.VendorOrderID)
if err = err2; err == nil {
order.Status = order2.Status
} else {
err = nil // ignore get status error
}
}
}
if err == nil {
rawDB := orm.NewOrm()
if _, err = orderman.FixedOrderManager.SaveOrder(order, false, rawDB); err != nil {
globals.SugarLogger.Debugf("CreateOrderFromOriginal abnormal orderID:%s, error:%v", orderOriginal.VendorOrderID, err)
}
} else {
globals.SugarLogger.Debugf("CreateOrderFromOriginal abnormal orderID:%s, error:%v", orderOriginal.VendorOrderID, err)
}
} else {
globals.SugarLogger.Debugf("CreateOrderFromOriginal abnormal orderID:%s", orderOriginal.VendorOrderID)
}
rawDB := orm.NewOrm()
db := dao.WrapDB(rawDB)
var orderList []*GoodsOrderOriginalEx
if err = dao.GetRows(db, &orderList, sql, sqlBatchCount); err != nil {
return nil, err
}, orderList)
// rootTask.AddChild(task).Run()
task.Run()
_, err = task.GetResult(0)
} else {
rootTask.Cancel()
}
return nil, err
}, math.MaxInt32)
}
if len(orderList) > 0 {
task := tasksch.NewParallelTask("CreateOrderFromOriginal", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError).SetParallelCount(1), ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
orderOriginal := batchItemList[0].(*GoodsOrderOriginalEx)
globals.SugarLogger.Debugf("CreateOrderFromOriginal processing orderID:%s", orderOriginal.VendorOrderID)
if handler := partner.GetPurchasePlatformFromVendorID(orderOriginal.VendorID); handler != nil {
var detail map[string]interface{}
if err = utils.UnmarshalUseNumber([]byte(strings.Replace(strings.Replace(orderOriginal.OriginalData, "\n", "", -1), "\r", "", -1)), &detail); err != nil {
globals.SugarLogger.Debugf("CreateOrderFromOriginal abnormal orderID:%s, error:%v", orderOriginal.VendorOrderID, err)
return nil, err
}
order := handler.Map2Order(detail)
if order.Status < model.OrderStatusEndBegin {
if orderOriginal.OrderStatus == 3 {
order.Status = model.OrderStatusFinished
} else if orderOriginal.OrderStatus == 7 {
order.Status = model.OrderStatusCanceled
} else {
order2, err2 := handler.GetOrder(order.VendorOrderID)
if err = err2; err == nil {
order.Status = order2.Status
} else {
err = nil // ignore get status error
}
}
}
if err == nil {
rawDB := orm.NewOrm()
if _, err = orderman.FixedOrderManager.SaveOrder(order, false, rawDB); err != nil {
globals.SugarLogger.Debugf("CreateOrderFromOriginal abnormal orderID:%s, error:%v", orderOriginal.VendorOrderID, err)
}
} else {
globals.SugarLogger.Debugf("CreateOrderFromOriginal abnormal orderID:%s, error:%v", orderOriginal.VendorOrderID, err)
}
} else {
globals.SugarLogger.Debugf("CreateOrderFromOriginal abnormal orderID:%s", orderOriginal.VendorOrderID)
}
return nil, err
}, orderList)
// rootTask.AddChild(task).Run()
task.Run()
_, err = task.GetResult(0)
} else {
rootTask.Cancel()
}
return nil, err
}, math.MaxInt32)
tasksch.ManageTask(rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
@@ -688,91 +695,93 @@ func TransformJdSpu2Sku(ctx *jxcontext.Context, skuNameIDs []int, count int, isA
return "", fmt.Errorf("待转换的skuName为空")
}
batchSize := 40
rootTask := tasksch.NewSeqTask("TransformJdSpu2Sku", ctx.GetUserName(), func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
var (
locker sync.Mutex
skuIDs []int
)
lastIndex := (step + 1) * batchSize
if lastIndex > len(skuNameList) {
lastIndex = len(skuNameList)
}
batchSkNameList := skuNameList[step*batchSize : lastIndex]
subTask := tasksch.NewParallelTask(fmt.Sprintf("TransformJdSpu2Sku:%d", step), tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx.GetUserName(), func(subTask *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
skuName := batchItemList[0].(*model.SkuName)
if !jxutils.IsFakeID(skuName.JdID) {
sql = `
rootTask := tasksch.NewSeqTask("TransformJdSpu2Sku", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
var (
locker sync.Mutex
skuIDs []int
)
lastIndex := (step + 1) * batchSize
if lastIndex > len(skuNameList) {
lastIndex = len(skuNameList)
}
batchSkNameList := skuNameList[step*batchSize : lastIndex]
subTask := tasksch.NewParallelTask(fmt.Sprintf("TransformJdSpu2Sku:%d", step), tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx,
func(subTask *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
skuName := batchItemList[0].(*model.SkuName)
if !jxutils.IsFakeID(skuName.JdID) {
sql = `
SELECT *
FROM sku
WHERE name_id = ? AND deleted_at = ? AND status <> ?;
`
sqlParams := []interface{}{
skuName.ID,
utils.DefaultTimeValue,
model.SkuStatusDeleted,
}
var skuList []*model.Sku
if err = dao.GetRows(db, &skuList, sql, sqlParams...); err != nil {
return "", err
}
globals.SugarLogger.Debugf("TransformJdSpu2Sku skuList:%s", utils.Format4Output(skuList, false))
if len(skuList) > 0 {
for _, sku := range skuList {
locker.Lock()
skuIDs = append(skuIDs, sku.ID)
locker.Unlock()
if !jxutils.IsFakeID(sku.JdID) {
if globals.EnableStoreWrite {
if err = api.JdAPI.UpdateSkuBaseInfo(utils.Int2Str(skuName.ID), utils.Int2Str(sku.ID), utils.Params2Map(jdapi.KeyFixedStatus, jdapi.SkuFixedStatusDeleted)); err != nil {
break
sqlParams := []interface{}{
skuName.ID,
utils.DefaultTimeValue,
model.SkuStatusDeleted,
}
var skuList []*model.Sku
if err = dao.GetRows(db, &skuList, sql, sqlParams...); err != nil {
return "", err
}
globals.SugarLogger.Debugf("TransformJdSpu2Sku skuList:%s", utils.Format4Output(skuList, false))
if len(skuList) > 0 {
for _, sku := range skuList {
locker.Lock()
skuIDs = append(skuIDs, sku.ID)
locker.Unlock()
if !jxutils.IsFakeID(sku.JdID) {
if globals.EnableStoreWrite {
if err = api.JdAPI.UpdateSkuBaseInfo(utils.Int2Str(skuName.ID), utils.Int2Str(sku.ID), utils.Params2Map(jdapi.KeyFixedStatus, jdapi.SkuFixedStatusDeleted)); err != nil {
break
}
}
}
}
}
}
}
if err == nil && globals.EnableStoreWrite {
if err = api.JdAPI.UpdateSpu(utils.Int2Str(skuName.ID), utils.Params2Map(jdapi.KeyFixedStatus, jdapi.SkuFixedStatusOffline)); err == nil {
err = api.JdAPI.UpdateSpu(utils.Int2Str(skuName.ID), utils.Params2Map(jdapi.KeyFixedStatus, jdapi.SkuFixedStatusDeleted))
}
}
if err == nil {
skuName.IsSpu = 0
skuName.JdID = 0
if _, err = dao.UpdateEntity(db, skuName, "IsSpu", "JdID"); err == nil {
sql := `
if err == nil && globals.EnableStoreWrite {
if err = api.JdAPI.UpdateSpu(utils.Int2Str(skuName.ID), utils.Params2Map(jdapi.KeyFixedStatus, jdapi.SkuFixedStatusOffline)); err == nil {
err = api.JdAPI.UpdateSpu(utils.Int2Str(skuName.ID), utils.Params2Map(jdapi.KeyFixedStatus, jdapi.SkuFixedStatusDeleted))
}
}
if err == nil {
skuName.IsSpu = 0
skuName.JdID = 0
if _, err = dao.UpdateEntity(db, skuName, "IsSpu", "JdID"); err == nil {
sql := `
UPDATE sku t1
SET
t1.jd_sync_status = ?,
t1.jd_id = 0
WHERE t1.name_id = ? AND t1.deleted_at = ? AND t1.status <> ?
`
sqlParams := []interface{}{
model.SyncFlagNewMask,
skuName.ID,
utils.DefaultTimeValue,
model.SkuStatusDeleted,
}
if _, err = dao.ExecuteSQL(db, sql, sqlParams...); err == nil {
_, err = cms.CurVendorSync.SyncSku(ctx, db, skuName.ID, -1, false, isContinueWhenError, ctx.GetUserName())
sqlParams := []interface{}{
model.SyncFlagNewMask,
skuName.ID,
utils.DefaultTimeValue,
model.SkuStatusDeleted,
}
if _, err = dao.ExecuteSQL(db, sql, sqlParams...); err == nil {
_, err = cms.CurVendorSync.SyncSku(ctx, db, skuName.ID, -1, false, isContinueWhenError, ctx.GetUserName())
}
}
}
} else {
globals.SugarLogger.Debugf("TransformJdSpu2Sku skuName:%d is fake", skuName.ID)
}
return nil, err
}, batchSkNameList)
rootTask.AddChild(subTask).Run()
if _, err = subTask.GetResult(0); err == nil {
if len(skuIDs) > 0 {
if _, err = dao.SetStoreSkuSyncStatus(db, model.VendorIDJD, -1, skuIDs, model.SyncFlagModifiedMask|model.SyncFlagPriceMask|model.SyncFlagSaleMask); err == nil {
time.Sleep(20 * time.Second)
_, err = cms.CurVendorSync.SyncStoresSkus(ctx, db, []int{model.VendorIDJD}, nil, skuIDs, false, isContinueWhenError)
}
}
} else {
globals.SugarLogger.Debugf("TransformJdSpu2Sku skuName:%d is fake", skuName.ID)
}
return nil, err
}, batchSkNameList)
rootTask.AddChild(subTask).Run()
if _, err = subTask.GetResult(0); err == nil {
if len(skuIDs) > 0 {
if _, err = dao.SetStoreSkuSyncStatus(db, model.VendorIDJD, -1, skuIDs, model.SyncFlagModifiedMask|model.SyncFlagPriceMask|model.SyncFlagSaleMask); err == nil {
time.Sleep(20 * time.Second)
_, err = cms.CurVendorSync.SyncStoresSkus(ctx, db, []int{model.VendorIDJD}, nil, skuIDs, false, isContinueWhenError)
}
}
}
return nil, err
}, (len(skuNameList)-1)/batchSize+1)
}, (len(skuNameList)-1)/batchSize+1)
tasksch.ManageTask(rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
@@ -795,21 +804,22 @@ func ReProcessJdBadComment(ctx *jxcontext.Context, isForce, isAsync, isContinueW
var commentList []*legacymodel.JxBadComments
if err = dao.GetRows(db, &commentList, sql); err == nil {
if len(commentList) > 0 {
rootTask := tasksch.NewParallelTask("ReProcessJdBadComment", nil, ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
badComment := batchItemList[0].(*legacymodel.JxBadComments)
comment1, _ := unmarshalCommentText(badComment.Msg)
comment2, _ := unmarshalCommentText(badComment.UpdatedMsg)
if len(comment1) > 0 {
badComment.Createtime = utils.Timestamp2Str(utils.MustInterface2Int64(comment1["createTime"].(map[string]interface{})["time"]) / 1000)
badComment.Msg = string(utils.MustMarshal(comment1))
if len(comment2) > 0 {
badComment.Updatetime = utils.Timestamp2Str(utils.MustInterface2Int64(comment2["createTime"].(map[string]interface{})["time"]) / 1000)
badComment.UpdatedMsg = string(utils.MustMarshal(comment2))
rootTask := tasksch.NewParallelTask("ReProcessJdBadComment", nil, ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
badComment := batchItemList[0].(*legacymodel.JxBadComments)
comment1, _ := unmarshalCommentText(badComment.Msg)
comment2, _ := unmarshalCommentText(badComment.UpdatedMsg)
if len(comment1) > 0 {
badComment.Createtime = utils.Timestamp2Str(utils.MustInterface2Int64(comment1["createTime"].(map[string]interface{})["time"]) / 1000)
badComment.Msg = string(utils.MustMarshal(comment1))
if len(comment2) > 0 {
badComment.Updatetime = utils.Timestamp2Str(utils.MustInterface2Int64(comment2["createTime"].(map[string]interface{})["time"]) / 1000)
badComment.UpdatedMsg = string(utils.MustMarshal(comment2))
}
_, err = dao.UpdateEntity(db, badComment)
}
_, err = dao.UpdateEntity(db, badComment)
}
return nil, err
}, commentList)
return nil, err
}, commentList)
tasksch.ManageTask(rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
@@ -856,15 +866,16 @@ func RefreshEbaiBadComment(ctx *jxcontext.Context, fromTime, toTime time.Time, i
}
days := int(toTime.Sub(fromTime)/(24*time.Hour) + 1)
globals.SugarLogger.Debugf("RefreshEbaiBadComment fromTime:%s, toTime:%s, days:%d", utils.Time2Str(fromTime), utils.Time2Str(toTime), days)
rootTask := tasksch.NewSeqTask("RefreshEbaiBadComment", ctx.GetUserName(), func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
batchFromTime := fromTime.Add(time.Duration(step) * 24 * time.Hour)
batchToTime := batchFromTime.Add(24*time.Hour - time.Second)
if batchToTime.Sub(toTime) > 0 {
batchToTime = toTime
}
err = ebai.CurPurchaseHandler.RefreshComment(batchFromTime, batchToTime)
return nil, err
}, days)
rootTask := tasksch.NewSeqTask("RefreshEbaiBadComment", ctx,
func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
batchFromTime := fromTime.Add(time.Duration(step) * 24 * time.Hour)
batchToTime := batchFromTime.Add(24*time.Hour - time.Second)
if batchToTime.Sub(toTime) > 0 {
batchToTime = toTime
}
err = ebai.CurPurchaseHandler.RefreshComment(batchFromTime, batchToTime)
return nil, err
}, days)
tasksch.ManageTask(rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)

View File

@@ -3,12 +3,10 @@ package jxcontext
import (
"errors"
"net/http"
"sync"
"git.rosy.net.cn/baseapi/utils"
"git.rosy.net.cn/jx-callback/business/auth2"
"git.rosy.net.cn/jx-callback/business/jxcallback/auth"
"git.rosy.net.cn/jx-callback/business/jxutils/tasksch"
"git.rosy.net.cn/jx-callback/business/model"
"git.rosy.net.cn/jx-callback/globals"
"github.com/astaxie/beego"
@@ -21,14 +19,12 @@ type IAuther interface {
}
type Context struct {
rootTask tasksch.ITask
token string
accessUUID string
userInfo IAuther //*auth.LoginInfo
w http.ResponseWriter
r *http.Request
mapData map[interface{}]interface{}
locker sync.RWMutex
}
const (
@@ -43,9 +39,8 @@ func init() {
AdminCtx = NewWithUserName(nil, model.AdminName, nil, nil)
}
func NewWithUserName(rootTask tasksch.ITask, userName string, w http.ResponseWriter, r *http.Request) (ctx *Context) {
func NewWithUserName(notUsed interface{}, userName string, w http.ResponseWriter, r *http.Request) (ctx *Context) {
ctx = &Context{
rootTask: rootTask,
token: userName,
w: w,
r: r,
@@ -55,9 +50,8 @@ func NewWithUserName(rootTask tasksch.ITask, userName string, w http.ResponseWri
return ctx
}
func New(rootTask tasksch.ITask, token string, w http.ResponseWriter, r *http.Request) (ctx *Context, errCode string, err error) {
func New(notUsed interface{}, token string, w http.ResponseWriter, r *http.Request) (ctx *Context, errCode string, err error) {
ctx = &Context{
rootTask: rootTask,
token: token,
w: w,
r: r,
@@ -141,34 +135,6 @@ func (ctx *Context) GetV2AuthInfo() (authInfo *auth2.AuthInfo, err error) {
return nil, auth2.ErrNeedV2Token
}
func (ctx *Context) GetRootTask() tasksch.ITask {
ctx.locker.RLock()
defer ctx.locker.RUnlock()
return ctx.rootTask
}
func (ctx *Context) SetTaskOrAddChild(task tasksch.ITask, parentTask tasksch.ITask) bool {
if parentTask != nil {
parentTask.AddChild(task)
} else {
parentTask = task
}
ctx.locker.RLock()
if ctx.rootTask == nil {
ctx.locker.RUnlock()
ctx.locker.Lock()
if ctx.rootTask == nil {
ctx.rootTask = parentTask
}
ctx.locker.Unlock()
return true
}
ctx.locker.RUnlock()
return false
}
func (ctx *Context) GetResponseWriter() http.ResponseWriter {
return ctx.w
}
@@ -176,17 +142,3 @@ func (ctx *Context) GetResponseWriter() http.ResponseWriter {
func (ctx *Context) GetRequest() *http.Request {
return ctx.r
}
func (ctx *Context) SetValue(key, value interface{}) {
ctx.locker.Lock()
defer ctx.locker.Unlock()
ctx.mapData[key] = value
}
func (ctx *Context) GetValue(key interface{}) interface{} {
ctx.locker.RLock()
defer ctx.locker.RUnlock()
return ctx.mapData[key]
}

View File

@@ -0,0 +1,24 @@
package msg
import (
"git.rosy.net.cn/jx-callback/business/auth2"
"git.rosy.net.cn/jx-callback/business/auth2/authprovider/dingding"
"git.rosy.net.cn/jx-callback/globals"
"git.rosy.net.cn/jx-callback/globals/api"
)
func SendUserMessage(userID, title, content string) (err error) {
authList, err := auth2.GetUserBindAuthInfo(userID)
if err == nil {
for _, auth := range authList {
if auth.Type == dingding.AuthTypeStaff {
err = api.DingDingAPI.CorpAsyncSendSimple(auth.AuthID, content)
break
}
}
}
if err != nil {
globals.SugarLogger.Infof("SendUserMessage userID:%s, title:%s, content:%s failed with error:%v", userID, title, content, err)
}
return err
}

View File

@@ -6,6 +6,7 @@ import (
"git.rosy.net.cn/baseapi/utils"
"git.rosy.net.cn/jx-callback/business/jxutils"
"git.rosy.net.cn/jx-callback/business/jxutils/jxcontext"
"git.rosy.net.cn/jx-callback/globals"
)
@@ -18,6 +19,8 @@ type WorkFunc func(task *ParallelTask, batchItemList []interface{}, params ...in
type ResultHandlerFunc func(taskName string, result []interface{}, err error)
type ParallelConfig struct {
// ParentTask ITask
// IsAsync bool
ParallelCount int
BatchSize int
IsContinueWhenError bool
@@ -41,9 +44,11 @@ var (
func NewParallelConfig() *ParallelConfig {
return &ParallelConfig{
// ParentTask: parentTask,
// IsAsync: false,
IsContinueWhenError: false,
ParallelCount: DefParallelCount,
BatchSize: 1,
IsContinueWhenError: false,
ResultHandler: nil,
}
}
@@ -63,12 +68,17 @@ func (c *ParallelConfig) SetIsContinueWhenError(isContinueWhenError bool) *Paral
return c
}
// func (c *ParallelConfig) SetIsAsync(isAsync bool) *ParallelConfig {
// c.IsAsync = isAsync
// return c
// }
func (c *ParallelConfig) SetResultHandler(resultHandler ResultHandlerFunc) *ParallelConfig {
c.ResultHandler = resultHandler
return c
}
func NewParallelTask(taskName string, config *ParallelConfig, userName string, worker WorkFunc, itemList interface{}, params ...interface{}) *ParallelTask {
func NewParallelTask(taskName string, config *ParallelConfig, ctx *jxcontext.Context, worker WorkFunc, itemList interface{}, params ...interface{}) *ParallelTask {
if config == nil {
config = NewParallelConfig()
}
@@ -91,7 +101,7 @@ func NewParallelTask(taskName string, config *ParallelConfig, userName string, w
worker: worker,
jobList: jobList,
}
task.Init(config.ParallelCount, config.BatchSize, config.IsContinueWhenError, params, taskName, userName, len(realItemList), jobListLen)
task.Init(config.ParallelCount, config.BatchSize, config.IsContinueWhenError, params, taskName, ctx, len(realItemList), jobListLen)
return task
}

View File

@@ -7,6 +7,7 @@ import (
"time"
"git.rosy.net.cn/baseapi/utils"
"git.rosy.net.cn/jx-callback/business/jxutils/jxcontext"
)
func TestRunParallelTask(t *testing.T) {
@@ -14,16 +15,17 @@ func TestRunParallelTask(t *testing.T) {
for k := range itemList {
itemList[k] = k
}
task := NewParallelTask("test", NewParallelConfig().SetParallelCount(100).SetBatchSize(7), "autotest", func(task *ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
sleepSecond := rand.Intn(5)
t.Logf("sleep %d seconds", sleepSecond)
time.Sleep(time.Duration(sleepSecond) * time.Second)
retSlice := make([]string, len(batchItemList))
for k := range retSlice {
retSlice[k] = "hello:" + utils.Int2Str(batchItemList[k].(int)*2)
}
return retSlice, nil
}, itemList, "a", "b", 1, 2)
task := NewParallelTask("test", NewParallelConfig().SetParallelCount(100).SetBatchSize(7), jxcontext.AdminCtx,
func(task *ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
sleepSecond := rand.Intn(5)
t.Logf("sleep %d seconds", sleepSecond)
time.Sleep(time.Duration(sleepSecond) * time.Second)
retSlice := make([]string, len(batchItemList))
for k := range retSlice {
retSlice[k] = "hello:" + utils.Int2Str(batchItemList[k].(int)*2)
}
return retSlice, nil
}, itemList, "a", "b", 1, 2)
task.Run()
result, err := task.GetResult(1 * time.Microsecond)
if err == nil || task.GetStatus() != TaskStatusWorking {
@@ -45,16 +47,17 @@ func TestCancelParallelTask(t *testing.T) {
for k := range itemList {
itemList[k] = k
}
task := NewParallelTask("test", NewParallelConfig().SetParallelCount(100).SetBatchSize(7), "autotest", func(task *ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
sleepSecond := rand.Intn(5)
fmt.Printf("sleep %d seconds\n", sleepSecond)
time.Sleep(time.Duration(sleepSecond) * time.Second)
retSlice := make([]string, len(batchItemList))
for k := range retSlice {
retSlice[k] = "hello:" + utils.Int2Str(batchItemList[k].(int)*2)
}
return retSlice, nil
}, itemList, "a", "b", 1, 2)
task := NewParallelTask("test", NewParallelConfig().SetParallelCount(100).SetBatchSize(7), jxcontext.AdminCtx,
func(task *ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
sleepSecond := rand.Intn(5)
fmt.Printf("sleep %d seconds\n", sleepSecond)
time.Sleep(time.Duration(sleepSecond) * time.Second)
retSlice := make([]string, len(batchItemList))
for k := range retSlice {
retSlice[k] = "hello:" + utils.Int2Str(batchItemList[k].(int)*2)
}
return retSlice, nil
}, itemList, "a", "b", 1, 2)
task.Run()
// time.Sleep(time.Second * 6)
fmt.Printf("finishedItemCount:%d, finishedJobCount:%d\n", task.GetFinishedItemCount(), task.GetFinishedJobCount())
@@ -71,19 +74,20 @@ func TestRunParallelTaskPartialSuccess(t *testing.T) {
for k := range itemList {
itemList[k] = k
}
task := NewParallelTask("test", NewParallelConfig().SetParallelCount(100).SetBatchSize(7).SetIsContinueWhenError(true), "autotest", func(task *ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
sleepSecond := rand.Intn(5)
t.Logf("sleep %d seconds", sleepSecond)
time.Sleep(time.Duration(sleepSecond) * time.Second)
retSlice := make([]string, len(batchItemList))
for k := range retSlice {
retSlice[k] = "hello:" + utils.Int2Str(batchItemList[k].(int)*2)
}
if rand.Intn(2) == 1 {
return nil, fmt.Errorf("test:%d", batchItemList[0].(int))
}
return retSlice, nil
}, itemList, "a", "b", 1, 2)
task := NewParallelTask("test", NewParallelConfig().SetParallelCount(100).SetBatchSize(7).SetIsContinueWhenError(true), jxcontext.AdminCtx,
func(task *ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
sleepSecond := rand.Intn(5)
t.Logf("sleep %d seconds", sleepSecond)
time.Sleep(time.Duration(sleepSecond) * time.Second)
retSlice := make([]string, len(batchItemList))
for k := range retSlice {
retSlice[k] = "hello:" + utils.Int2Str(batchItemList[k].(int)*2)
}
if rand.Intn(2) == 1 {
return nil, fmt.Errorf("test:%d", batchItemList[0].(int))
}
return retSlice, nil
}, itemList, "a", "b", 1, 2)
task.Run()
result, err := task.GetResult(1 * time.Microsecond)
if err == nil || task.GetStatus() != TaskStatusWorking {

View File

@@ -4,6 +4,7 @@ import (
"time"
"git.rosy.net.cn/baseapi/utils"
"git.rosy.net.cn/jx-callback/business/jxutils/jxcontext"
"git.rosy.net.cn/jx-callback/globals"
)
@@ -19,11 +20,11 @@ type SeqTask struct {
worker SeqWorkFunc
}
func NewSeqTask(taskName string, userName string, worker SeqWorkFunc, stepCount int, params ...interface{}) *SeqTask {
func NewSeqTask(taskName string, ctx *jxcontext.Context, worker SeqWorkFunc, stepCount int, params ...interface{}) *SeqTask {
task := &SeqTask{
worker: worker,
}
task.Init(1, 1, false, params, taskName, userName, stepCount, stepCount)
task.Init(1, 1, false, params, taskName, ctx, stepCount, stepCount)
return task
}

View File

@@ -7,38 +7,41 @@ import (
"time"
"git.rosy.net.cn/baseapi/utils"
"git.rosy.net.cn/jx-callback/business/jxutils/jxcontext"
)
func TestRunSeqTask(t *testing.T) {
var seqTask ITask
seqTask = NewSeqTask("TestSeqTask", "autotest", func(task *SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
fmt.Println("ONE")
task2 := NewParallelTask("hello", nil, "xjh", func(parallelTask *ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
i := batchItemList[0].(int)
time.Sleep(2 * time.Second)
fmt.Println(i * 2)
return nil, nil
}, []int{1, 2, 3})
seqTask.AddChild(task2)
time.Sleep(time.Duration(rand.Intn(3)) * time.Second)
task2.Run()
case 1:
fmt.Println("TWO")
time.Sleep(time.Duration(rand.Intn(3)) * time.Second)
case 2:
fmt.Println("THREE")
time.Sleep(time.Duration(rand.Intn(3)) * time.Second)
case 3:
fmt.Println("FOUR")
time.Sleep(time.Duration(rand.Intn(3)) * time.Second)
case 4:
fmt.Println("FIVE")
time.Sleep(time.Duration(rand.Intn(3)) * time.Second)
}
return []string{"1"}, nil
}, 5)
seqTask = NewSeqTask("TestSeqTask", jxcontext.AdminCtx,
func(task *SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
fmt.Println("ONE")
task2 := NewParallelTask("hello", nil, jxcontext.AdminCtx,
func(parallelTask *ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
i := batchItemList[0].(int)
time.Sleep(2 * time.Second)
fmt.Println(i * 2)
return nil, nil
}, []int{1, 2, 3})
seqTask.AddChild(task2)
time.Sleep(time.Duration(rand.Intn(3)) * time.Second)
task2.Run()
case 1:
fmt.Println("TWO")
time.Sleep(time.Duration(rand.Intn(3)) * time.Second)
case 2:
fmt.Println("THREE")
time.Sleep(time.Duration(rand.Intn(3)) * time.Second)
case 3:
fmt.Println("FOUR")
time.Sleep(time.Duration(rand.Intn(3)) * time.Second)
case 4:
fmt.Println("FIVE")
time.Sleep(time.Duration(rand.Intn(3)) * time.Second)
}
return []string{"1"}, nil
}, 5)
seqTask.Run()
time.Sleep(3 * time.Second)

View File

@@ -8,6 +8,8 @@ import (
"time"
"git.rosy.net.cn/baseapi/utils"
"git.rosy.net.cn/jx-callback/business/jxutils/jxcontext"
"git.rosy.net.cn/jx-callback/business/jxutils/msg"
"git.rosy.net.cn/jx-callback/globals"
)
@@ -97,14 +99,17 @@ type BaseTask struct {
Children TaskList `json:"children"`
Err error `json:"err"`
detailErrMsgList []string `json:"-"`
finishChan chan int
C <-chan int `json:"-"`
detailErrMsgList []string
finishChan chan struct{}
C <-chan struct{} `json:"-"`
params []interface{}
quitChan chan int
locker sync.RWMutex
parent ITask
ctx *jxcontext.Context
isGetResultCalled bool
}
func (s TaskList) Len() int {
@@ -121,7 +126,7 @@ func (s TaskList) Swap(i, j int) {
s[j] = tmp
}
func (t *BaseTask) Init(parallelCount, batchSize int, isContinueWhenError bool, params []interface{}, name, userName string, totalItemCount, totalJobCount int) {
func (t *BaseTask) Init(parallelCount, batchSize int, isContinueWhenError bool, params []interface{}, name string, ctx *jxcontext.Context, totalItemCount, totalJobCount int) {
t.ID = utils.GetUUID()
t.ParallelCount = parallelCount
t.BatchSize = batchSize
@@ -129,13 +134,14 @@ func (t *BaseTask) Init(parallelCount, batchSize int, isContinueWhenError bool,
t.params = params
t.Name = name
t.CreatedAt = time.Now()
t.CreatedBy = userName
t.ctx = ctx
t.CreatedBy = ctx.GetUserName()
t.UpdatedAt = t.CreatedAt
t.TerminatedAt = utils.DefaultTimeValue
t.TotalItemCount = totalItemCount
t.TotalJobCount = totalJobCount
t.quitChan = make(chan int)
t.finishChan = make(chan int)
t.finishChan = make(chan struct{})
t.Status = TaskStatusWorking
t.C = t.finishChan
@@ -155,6 +161,7 @@ func (t *BaseTask) GetResult(duration time.Duration) (retVal []interface{}, err
timer := time.NewTimer(duration)
select {
case <-t.finishChan:
t.isGetResultCalled = true
timer.Stop()
return t.Result, t.Err
case <-timer.C:
@@ -249,6 +256,14 @@ func AddChild(parentTask ITask, task ITask) ITask {
return task
}
func HandleTask(task, parentTask ITask, isMangeIt bool) ITask {
AddChild(task, parentTask)
if parentTask == nil && isMangeIt {
ManageTask(task)
}
return task
}
/////////
func (t *BaseTask) MarshalJSON() ([]byte, error) {
@@ -280,6 +295,18 @@ func (t *BaseTask) run(taskHandler func()) {
}
close(t.finishChan)
time.Sleep(10 * time.Millisecond) // 等待GetResult中的isGetResultCalled赋值
if !t.isGetResultCalled && t.parent == nil && len(GetTasks(t.ID, TaskStatusBegin, TaskStatusEnd, 24, "")) == 0 {
if authInfo, err := t.ctx.GetV2AuthInfo(); err == nil { // 这里应该是不管登录类型,直接以可能的方式发消息
var content string
if t.Status == TaskStatusFinished {
content = fmt.Sprintf("你的异步任务[%s]执行成功完成", t.Name)
} else {
content = fmt.Sprintf("你的异步任务[%s]执行失败,%s", t.Name, t.Err.Error())
}
msg.SendUserMessage(authInfo.UserID, "异步任务完成", content)
}
}
})
}
}

View File

@@ -52,3 +52,18 @@ func GetAuthBindsByAuthID2(db *DaoDB, authID2 string, typeList []string) (authBi
err = GetRows(db, &authBinds, sql, sqlParams...)
return authBinds, err
}
func GetUserBindAuthInfo(db *DaoDB, userID string) (authList []*model.AuthBind, err error) {
sql := `
SELECT *
FROM auth_bind t1
WHERE t1.deleted_at = ? AND t1.status = ? AND t1.user_id = ?
`
sqlParams := []interface{}{
utils.DefaultTimeValue,
model.UserStatusNormal,
userID,
}
err = GetRows(db, &authList, sql, sqlParams...)
return authList, err
}

View File

@@ -23,18 +23,3 @@ func GetUserByID(db *DaoDB, fieldName, fieldValue string) (user *model.User, err
err = GetRow(db, &user, sql, sqlParams...)
return user, err
}
func GetUserBindAuthInfo(db *DaoDB, userID string) (authList []*model.AuthBind, err error) {
sql := `
SELECT *
FROM auth_bind t1
WHERE t1.deleted_at = ? AND t1.status = ? AND t1.user_id = ?
`
sqlParams := []interface{}{
utils.DefaultTimeValue,
model.UserStatusNormal,
userID,
}
err = GetRows(db, &authList, sql, sqlParams...)
return authList, err
}

View File

@@ -3,6 +3,7 @@ package ebai
import (
"git.rosy.net.cn/baseapi/platformapi/ebaiapi"
"git.rosy.net.cn/baseapi/utils"
"git.rosy.net.cn/jx-callback/business/jxutils/jxcontext"
"git.rosy.net.cn/jx-callback/business/jxutils/tasksch"
"git.rosy.net.cn/jx-callback/globals"
"git.rosy.net.cn/jx-callback/globals/api"
@@ -11,30 +12,31 @@ import (
func (p *PurchaseHandler) UpdatePlaces() (err error) {
provinces, err := api.EbaiAPI.CommonShopCities(0)
if err == nil {
task := tasksch.NewParallelTask("UpdatePlaces", nil, "test", func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
province := batchItemList[0].(*ebaiapi.CityInfo)
retSlice := make([]*ebaiapi.CityInfo, 0)
if province.IsOpen != 0 {
retSlice = append(retSlice, province)
cities, err := api.EbaiAPI.CommonShopCities(province.ID)
for _, city := range cities {
if city.IsOpen != 0 {
retSlice = append(retSlice, city)
districts, err2 := api.EbaiAPI.CommonShopCities(city.ID)
if err = err2; err == nil {
for _, district := range districts {
if district.IsOpen != 0 {
retSlice = append(retSlice, district)
task := tasksch.NewParallelTask("UpdatePlaces", nil, jxcontext.AdminCtx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
province := batchItemList[0].(*ebaiapi.CityInfo)
retSlice := make([]*ebaiapi.CityInfo, 0)
if province.IsOpen != 0 {
retSlice = append(retSlice, province)
cities, err := api.EbaiAPI.CommonShopCities(province.ID)
for _, city := range cities {
if city.IsOpen != 0 {
retSlice = append(retSlice, city)
districts, err2 := api.EbaiAPI.CommonShopCities(city.ID)
if err = err2; err == nil {
for _, district := range districts {
if district.IsOpen != 0 {
retSlice = append(retSlice, district)
}
}
} else {
break
}
} else {
break
}
}
}
}
return retSlice, err
}, provinces)
return retSlice, err
}, provinces)
task.Run()
places, err2 := task.GetResult(0)
if err = err2; err == nil {

View File

@@ -338,17 +338,17 @@ func (c *PurchaseHandler) RefreshRealMobile(ctx *jxcontext.Context, fromTime, to
var orderList []*model.GoodsOrder
db := dao.GetDB()
if err = dao.GetRows(db, &orderList, sql, sqlParams...); err == nil && len(orderList) > 0 {
task := tasksch.NewParallelTask("ebai RefreshRealMobile", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
order := batchItemList[0].(*model.GoodsOrder)
mobile, err2 := api.EbaiAPI.GetRealMobile4Order(order.VendorOrderID)
if err = err2; err == nil && !jxutils.IsMobileFake(mobile) && strings.Index(order.ConsigneeMobile, mobile) == -1 {
order.ConsigneeMobile2 = mobile
_, err = dao.UpdateEntity(db, order, "ConsigneeMobile2")
}
return nil, err
}, orderList)
ctx.SetTaskOrAddChild(task, nil)
tasksch.ManageTask(task).Run()
task := tasksch.NewParallelTask("ebai RefreshRealMobile", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
order := batchItemList[0].(*model.GoodsOrder)
mobile, err2 := api.EbaiAPI.GetRealMobile4Order(order.VendorOrderID)
if err = err2; err == nil && !jxutils.IsMobileFake(mobile) && strings.Index(order.ConsigneeMobile, mobile) == -1 {
order.ConsigneeMobile2 = mobile
_, err = dao.UpdateEntity(db, order, "ConsigneeMobile2")
}
return nil, err
}, orderList)
tasksch.HandleTask(task, nil, true).Run()
hint = task.ID
if !isAsync {
_, err = task.GetResult(0)

View File

@@ -216,44 +216,45 @@ func (p *PurchaseHandler) RefreshAllStoresID(ctx *jxcontext.Context, parentTask
const stepCount = 3
var stores []*tEbaiStoreInfo
db := dao.GetDB()
rootTask := tasksch.NewSeqTask("ebai RefreshAllStoresID", ctx.GetUserName(), func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = dao.GetRows(db, &stores, `
rootTask := tasksch.NewSeqTask("ebai RefreshAllStoresID", ctx,
func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = dao.GetRows(db, &stores, `
SELECT t1.*, t2.vendor_store_id
FROM store t1
JOIN store_map t2 ON t1.id = t2.store_id AND t2.deleted_at = ? AND t2.vendor_id = ?
WHERE t1.deleted_at = ?
`, utils.DefaultTimeValue, model.VendorIDEBAI, utils.DefaultTimeValue)
default:
taskName := "ebai RefreshAllStoresID update to custom id"
if step != stepCount-1 {
taskName = "ebai RefreshAllStoresID update to uuid"
default:
taskName := "ebai RefreshAllStoresID update to custom id"
if step != stepCount-1 {
taskName = "ebai RefreshAllStoresID update to uuid"
}
task1 := tasksch.NewParallelTask(taskName, tasksch.NewParallelConfig().SetBatchSize(batchSize), ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
baiduShopIDs := make([]string, len(batchItemList))
shopIDs := make([]string, len(batchItemList))
for k, v := range batchItemList {
store := v.(*tEbaiStoreInfo)
baiduShopIDs[k] = store.VendorStoreID
shopIDs[k] = utils.Int2Str(store.ID)
if step != stepCount-1 {
shopIDs[k] = utils.GetUUID()
}
}
if globals.EnableStoreWrite && globals.EnableEbaiStoreWrite {
err = api.EbaiAPI.ShopIDBatchUpdate(baiduShopIDs, shopIDs)
}
return nil, err
}, stores)
task.AddChild(task1).Run()
_, err = task1.GetResult(0)
}
task1 := tasksch.NewParallelTask(taskName, tasksch.NewParallelConfig().SetBatchSize(batchSize), ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
baiduShopIDs := make([]string, len(batchItemList))
shopIDs := make([]string, len(batchItemList))
for k, v := range batchItemList {
store := v.(*tEbaiStoreInfo)
baiduShopIDs[k] = store.VendorStoreID
shopIDs[k] = utils.Int2Str(store.ID)
if step != stepCount-1 {
shopIDs[k] = utils.GetUUID()
}
}
if globals.EnableStoreWrite && globals.EnableEbaiStoreWrite {
err = api.EbaiAPI.ShopIDBatchUpdate(baiduShopIDs, shopIDs)
}
return nil, err
}, stores)
task.AddChild(task1).Run()
_, err = task1.GetResult(0)
}
return nil, err
}, stepCount)
return nil, err
}, stepCount)
ctx.SetTaskOrAddChild(rootTask, parentTask)
rootTask.Run()
tasksch.HandleTask(rootTask, parentTask, false).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
}

View File

@@ -144,29 +144,30 @@ func (p *PurchaseHandler) FullSyncStoreSkus(ctx *jxcontext.Context, parentTask t
globals.SugarLogger.Debugf("FullSyncStoreSkus storeID:%d, isContinueWhenError:%t, userName:%s", storeID, isContinueWhenError, userName)
db := dao.GetDB()
rootTask := tasksch.NewSeqTask("FullSyncStoreSkus", userName, func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = p.DeleteRemoteSkus(ctx, rootTask, storeID, nil)
// 强制忽略删除SKU错误
if isContinueWhenError {
err = nil
rootTask := tasksch.NewSeqTask("FullSyncStoreSkus", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = p.DeleteRemoteSkus(ctx, rootTask, storeID, nil)
// 强制忽略删除SKU错误
if isContinueWhenError {
err = nil
}
case 1:
_, err = p.setStoreSkuSyncStatus(ctx, db, storeID, nil, model.SyncFlagNewMask)
case 2:
if err = p.DeleteRemoteCategories(ctx, rootTask, storeID, nil); err == nil {
_, err = dao.SetStoreCategorySyncStatus(db, model.VendorIDEBAI, storeID, nil, model.SyncFlagNewMask)
}
case 3:
err = p.SyncLocalStoreCategory(db, storeID, userName)
case 4:
_, err = p.SyncStoreCategory(ctx, rootTask, storeID, false)
case 5:
_, err = p.SyncStoreSkus(ctx, rootTask, storeID, nil, false, isContinueWhenError)
}
case 1:
_, err = p.setStoreSkuSyncStatus(ctx, db, storeID, nil, model.SyncFlagNewMask)
case 2:
if err = p.DeleteRemoteCategories(ctx, rootTask, storeID, nil); err == nil {
_, err = dao.SetStoreCategorySyncStatus(db, model.VendorIDEBAI, storeID, nil, model.SyncFlagNewMask)
}
case 3:
err = p.SyncLocalStoreCategory(db, storeID, userName)
case 4:
_, err = p.SyncStoreCategory(ctx, rootTask, storeID, false)
case 5:
_, err = p.SyncStoreSkus(ctx, rootTask, storeID, nil, false, isContinueWhenError)
}
return nil, err
}, 6)
return nil, err
}, 6)
tasksch.AddChild(parentTask, rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
@@ -180,24 +181,25 @@ func (p *PurchaseHandler) DeleteRemoteStoreSkus(ctx *jxcontext.Context, parentTa
db := dao.GetDB()
var errDeleteSku error
rootTask := tasksch.NewSeqTask("DeleteRemoteStoreSkus", userName, func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = p.DeleteRemoteSkus(ctx, rootTask, storeID, nil)
errDeleteSku = err
// 强制忽略删除SKU错误
if isContinueWhenError {
err = nil
rootTask := tasksch.NewSeqTask("DeleteRemoteStoreSkus", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = p.DeleteRemoteSkus(ctx, rootTask, storeID, nil)
errDeleteSku = err
// 强制忽略删除SKU错误
if isContinueWhenError {
err = nil
}
case 1:
_, err = p.setStoreSkuSyncStatus(ctx, db, storeID, nil, model.SyncFlagNewMask)
case 2:
if err = p.DeleteRemoteCategories(ctx, rootTask, storeID, nil); err == nil {
_, err = dao.SetStoreCategorySyncStatus(db, model.VendorIDEBAI, storeID, nil, model.SyncFlagNewMask)
}
}
case 1:
_, err = p.setStoreSkuSyncStatus(ctx, db, storeID, nil, model.SyncFlagNewMask)
case 2:
if err = p.DeleteRemoteCategories(ctx, rootTask, storeID, nil); err == nil {
_, err = dao.SetStoreCategorySyncStatus(db, model.VendorIDEBAI, storeID, nil, model.SyncFlagNewMask)
}
}
return nil, err
}, 3)
return nil, err
}, 3)
tasksch.AddChild(parentTask, rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
@@ -215,58 +217,60 @@ func (p *PurchaseHandler) SyncStoreSkus(ctx *jxcontext.Context, parentTask tasks
var storeSkuInfoList []*tStoreSkuFullInfo
var num int64
strStoreID := utils.Int2Str(storeID)
rootTask := tasksch.NewSeqTask("SyncStoreSkus饿百1", userName, func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
if step == 0 {
db := dao.GetDB()
for i := 0; i < 3; i++ {
if storeSkuInfoList, err = p.getDirtyStoreSkus(db, storeID, skuIDs); err != nil {
return nil, err
}
if num, err = p.createCatByStoreSkus(ctx, rootTask, db, storeID, storeSkuInfoList); err != nil {
return nil, err
}
if num == 0 {
break
}
}
if num != 0 {
globals.SugarLogger.Infof("SyncStoreSkus 不能创建商品所需的类别, storeID:%d, skuIDs:%v, isContinueWhenError:%t, userName:%s", storeID, skuIDs, isContinueWhenError, userName)
return nil, errors.New("不能创建商品所需的类别")
}
} else if step == 1 {
task := tasksch.NewParallelTask("SyncStoreSkus饿百2", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), userName, func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
storeSku := batchItemList[0].(*tStoreSkuFullInfo)
updateFields := []string{model.FieldEbaiSyncStatus}
if globals.EnableStoreWrite && globals.EnableEbaiStoreWrite {
if storeSku.EbaiSyncStatus&model.SyncFlagDeletedMask != 0 {
err = api.EbaiAPI.SkuDelete(strStoreID, utils.Int64ToStr(storeSku.EbaiID))
} else if storeSku.EbaiSyncStatus&model.SyncFlagNewMask != 0 {
// globals.SugarLogger.Debug(utils.Format4Output(genSkuParamsFromStoreSkuInfo(storeSku), false))
// todo 适当处理重复(即已经创建)的情况
if storeSku.EbaiID, err = api.EbaiAPI.SkuCreate(strStoreID, storeSku.SkuID, genSkuParamsFromStoreSkuInfo(storeSku)); err == nil {
updateFields = append(updateFields, model.FieldEbaiID)
}
} else if storeSku.EbaiSyncStatus&model.SyncFlagModifiedMask != 0 {
if jxutils.IsFakeID(storeSku.EbaiID) {
err = fmt.Errorf("京西数据异常,修改一个没有创建的饿百商品:%d, store:%s", storeSku.SkuID, strStoreID)
} else {
if _, err = api.EbaiAPI.SkuUpdate(strStoreID, storeSku.EbaiID, genSkuParamsFromStoreSkuInfo(storeSku)); err == nil {
// err = api.EbaiAPI.SkuShopCategoryMap(strStoreID, storeSku.EbaiID, utils.Int64ToStr(storeSku.CatEbaiID))
}
}
rootTask := tasksch.NewSeqTask("SyncStoreSkus饿百1", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
if step == 0 {
db := dao.GetDB()
for i := 0; i < 3; i++ {
if storeSkuInfoList, err = p.getDirtyStoreSkus(db, storeID, skuIDs); err != nil {
return nil, err
}
if num, err = p.createCatByStoreSkus(ctx, rootTask, db, storeID, storeSkuInfoList); err != nil {
return nil, err
}
if num == 0 {
break
}
}
if err == nil {
storeSku.EbaiSyncStatus = 0
_, err = dao.UpdateEntity(nil, &storeSku.StoreSkuBind, updateFields...)
if num != 0 {
globals.SugarLogger.Infof("SyncStoreSkus 不能创建商品所需的类别, storeID:%d, skuIDs:%v, isContinueWhenError:%t, userName:%s", storeID, skuIDs, isContinueWhenError, userName)
return nil, errors.New("不能创建商品所需的类别")
}
return nil, err
}, storeSkuInfoList)
tasksch.AddChild(rootTask, task).Run()
_, err = task.GetResult(0)
}
return nil, err
}, 2)
} else if step == 1 {
task := tasksch.NewParallelTask("SyncStoreSkus饿百2", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
storeSku := batchItemList[0].(*tStoreSkuFullInfo)
updateFields := []string{model.FieldEbaiSyncStatus}
if globals.EnableStoreWrite && globals.EnableEbaiStoreWrite {
if storeSku.EbaiSyncStatus&model.SyncFlagDeletedMask != 0 {
err = api.EbaiAPI.SkuDelete(strStoreID, utils.Int64ToStr(storeSku.EbaiID))
} else if storeSku.EbaiSyncStatus&model.SyncFlagNewMask != 0 {
// globals.SugarLogger.Debug(utils.Format4Output(genSkuParamsFromStoreSkuInfo(storeSku), false))
// todo 适当处理重复(即已经创建)的情况
if storeSku.EbaiID, err = api.EbaiAPI.SkuCreate(strStoreID, storeSku.SkuID, genSkuParamsFromStoreSkuInfo(storeSku)); err == nil {
updateFields = append(updateFields, model.FieldEbaiID)
}
} else if storeSku.EbaiSyncStatus&model.SyncFlagModifiedMask != 0 {
if jxutils.IsFakeID(storeSku.EbaiID) {
err = fmt.Errorf("京西数据异常,修改一个没有创建的饿百商品:%d, store:%s", storeSku.SkuID, strStoreID)
} else {
if _, err = api.EbaiAPI.SkuUpdate(strStoreID, storeSku.EbaiID, genSkuParamsFromStoreSkuInfo(storeSku)); err == nil {
// err = api.EbaiAPI.SkuShopCategoryMap(strStoreID, storeSku.EbaiID, utils.Int64ToStr(storeSku.CatEbaiID))
}
}
}
}
if err == nil {
storeSku.EbaiSyncStatus = 0
_, err = dao.UpdateEntity(nil, &storeSku.StoreSkuBind, updateFields...)
}
return nil, err
}, storeSkuInfoList)
tasksch.AddChild(rootTask, task).Run()
_, err = task.GetResult(0)
}
return nil, err
}, 2)
tasksch.AddChild(parentTask, rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
@@ -274,7 +278,7 @@ func (p *PurchaseHandler) SyncStoreSkus(ctx *jxcontext.Context, parentTask tasks
return rootTask.ID, err
}
func (p *PurchaseHandler) GetAllRemoteSkus(storeID int) (skus []map[string]interface{}, err error) {
func (p *PurchaseHandler) GetAllRemoteSkus(ctx *jxcontext.Context, storeID int, parentTask tasksch.ITask) (skus []map[string]interface{}, err error) {
page1, err := api.EbaiAPI.SkuList(utils.Int2Str(storeID), utils.Params2Map("pagesize", MaxPageSize))
if err == nil {
skus = append(skus, page1.List...)
@@ -283,19 +287,20 @@ func (p *PurchaseHandler) GetAllRemoteSkus(storeID int) (skus []map[string]inter
for i := 2; i <= page1.Pages; i++ {
pages[i-2] = i
}
task := tasksch.NewParallelTask("GetAllRemoteSkus", nil, "", func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
callParams := map[string]interface{}{
"pagesize": MaxPageSize,
"page": batchItemList[0],
}
pageSku, err2 := api.EbaiAPI.SkuList(utils.Int2Str(storeID), callParams)
if err2 == nil {
return pageSku.List, err2
}
globals.SugarLogger.Debug(utils.Format4Output(callParams, false))
return nil, err2
}, pages)
task.Run()
task := tasksch.NewParallelTask("GetAllRemoteSkus", nil, ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
callParams := map[string]interface{}{
"pagesize": MaxPageSize,
"page": batchItemList[0],
}
pageSku, err2 := api.EbaiAPI.SkuList(utils.Int2Str(storeID), callParams)
if err2 == nil {
return pageSku.List, err2
}
globals.SugarLogger.Debug(utils.Format4Output(callParams, false))
return nil, err2
}, pages)
tasksch.HandleTask(task, parentTask, false).Run()
result, err2 := task.GetResult(0)
if err = err2; err == nil {
for _, v := range result {
@@ -311,7 +316,7 @@ func (p *PurchaseHandler) DeleteRemoteSkus(ctx *jxcontext.Context, parentTask ta
globals.SugarLogger.Debugf("DeleteRemoteSkus饿百 storeID:%d", storeID)
if vendorSkuIDs == nil {
result, err2 := p.GetAllRemoteSkus(storeID)
result, err2 := p.GetAllRemoteSkus(ctx, storeID, parentTask)
if err = err2; err == nil {
vendorSkuIDs = make([]string, len(result))
for k, v := range result {
@@ -319,16 +324,17 @@ func (p *PurchaseHandler) DeleteRemoteSkus(ctx *jxcontext.Context, parentTask ta
}
}
}
task := tasksch.NewParallelTask("DeleteRemoteSkus", tasksch.NewParallelConfig().SetBatchSize(100).SetIsContinueWhenError(true), "", func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
strList := make([]string, len(batchItemList))
for k, v := range batchItemList {
strList[k] = v.(string)
}
if globals.EnableStoreWrite && globals.EnableEbaiStoreWrite {
err = api.EbaiAPI.SkuDelete(utils.Int2Str(storeID), strings.Join(strList, ","))
}
return nil, err
}, vendorSkuIDs)
task := tasksch.NewParallelTask("DeleteRemoteSkus", tasksch.NewParallelConfig().SetBatchSize(100).SetIsContinueWhenError(true), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
strList := make([]string, len(batchItemList))
for k, v := range batchItemList {
strList[k] = v.(string)
}
if globals.EnableStoreWrite && globals.EnableEbaiStoreWrite {
err = api.EbaiAPI.SkuDelete(utils.Int2Str(storeID), strings.Join(strList, ","))
}
return nil, err
}, vendorSkuIDs)
tasksch.AddChild(parentTask, task).Run()
_, err = task.GetResult(0)
return err
@@ -347,12 +353,13 @@ func (p *PurchaseHandler) DeleteRemoteCategories(ctx *jxcontext.Context, parentT
}
}
}
task := tasksch.NewParallelTask("DeleteRemoteCategories", tasksch.NewParallelConfig().SetIsContinueWhenError(true), "", func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
if globals.EnableStoreWrite && globals.EnableEbaiStoreWrite {
err = api.EbaiAPI.ShopCategoryDelete(strStoreID, batchItemList[0].(int64))
}
return nil, err
}, vendorCatIDs)
task := tasksch.NewParallelTask("DeleteRemoteCategories", tasksch.NewParallelConfig().SetIsContinueWhenError(true), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
if globals.EnableStoreWrite && globals.EnableEbaiStoreWrite {
err = api.EbaiAPI.ShopCategoryDelete(strStoreID, batchItemList[0].(int64))
}
return nil, err
}, vendorCatIDs)
tasksch.AddChild(parentTask, task).Run()
_, err = task.GetResult(0)
return err
@@ -465,9 +472,10 @@ func (p *PurchaseHandler) SyncStoreCategory(ctx *jxcontext.Context, parentTask t
globals.SugarLogger.Debugf("SyncOneStoreCategories storeID:%d, userName:%s", storeID, userName)
db := dao.GetDB()
rootTask := tasksch.NewSeqTask("ebai SyncStoreCategory", userName, func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
level := step + 1
sql := `
rootTask := tasksch.NewSeqTask("ebai SyncStoreCategory", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
level := step + 1
sql := `
SELECT t2.*, t1.name, t1.parent_id, t1.level, t1.type, t1.seq, t2p.ebai_id parent_ebai_id
FROM sku_category t1
LEFT JOIN sku_category t1p ON t1.parent_id = t1p.id
@@ -475,45 +483,46 @@ func (p *PurchaseHandler) SyncStoreCategory(ctx *jxcontext.Context, parentTask t
LEFT JOIN store_sku_category_map t2p ON t1p.id = t2p.category_id AND t2p.store_id = ? AND t2p.deleted_at = ?
WHERE t1.level = ? AND t1.deleted_at = ?
`
var catList []*tStoreCatInfo
sqlParams := []interface{}{
storeID,
storeID,
utils.DefaultTimeValue,
level,
utils.DefaultTimeValue,
}
if err = dao.GetRows(db, &catList, sql, sqlParams...); err == nil {
strStoreID := utils.Int2Str(storeID)
task := tasksch.NewParallelTask("SyncStoreCategory", nil, userName, func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
updateFields := []string{model.FieldEbaiSyncStatus}
catInfo := batchItemList[0].(*tStoreCatInfo)
// globals.SugarLogger.Debug(utils.Format4Output(catInfo, false))
if globals.EnableStoreWrite && globals.EnableEbaiStoreWrite {
if catInfo.EbaiSyncStatus&model.SyncFlagDeletedMask != 0 { // 删除
err = api.EbaiAPI.ShopCategoryDelete(strStoreID, catInfo.EbaiID)
} else if catInfo.EbaiSyncStatus&model.SyncFlagNewMask != 0 { // 新增
ebaiID, err2 := api.EbaiAPI.ShopCategoryCreate(strStoreID, catInfo.ParentEbaiID, formatName(catInfo.Name), jxCatSeq2Ebai(catInfo.Seq))
if err = err2; err == nil {
catInfo.EbaiID = ebaiID
updateFields = append(updateFields, model.FieldEbaiID)
var catList []*tStoreCatInfo
sqlParams := []interface{}{
storeID,
storeID,
utils.DefaultTimeValue,
level,
utils.DefaultTimeValue,
}
if err = dao.GetRows(db, &catList, sql, sqlParams...); err == nil {
strStoreID := utils.Int2Str(storeID)
task := tasksch.NewParallelTask("SyncStoreCategory", nil, ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
updateFields := []string{model.FieldEbaiSyncStatus}
catInfo := batchItemList[0].(*tStoreCatInfo)
// globals.SugarLogger.Debug(utils.Format4Output(catInfo, false))
if globals.EnableStoreWrite && globals.EnableEbaiStoreWrite {
if catInfo.EbaiSyncStatus&model.SyncFlagDeletedMask != 0 { // 删除
err = api.EbaiAPI.ShopCategoryDelete(strStoreID, catInfo.EbaiID)
} else if catInfo.EbaiSyncStatus&model.SyncFlagNewMask != 0 { // 新增
ebaiID, err2 := api.EbaiAPI.ShopCategoryCreate(strStoreID, catInfo.ParentEbaiID, formatName(catInfo.Name), jxCatSeq2Ebai(catInfo.Seq))
if err = err2; err == nil {
catInfo.EbaiID = ebaiID
updateFields = append(updateFields, model.FieldEbaiID)
}
} else if catInfo.EbaiSyncStatus&model.SyncFlagModifiedMask != 0 { // 修改
err = api.EbaiAPI.ShopCategoryUpdate(strStoreID, catInfo.EbaiID, formatName(catInfo.Name), jxCatSeq2Ebai(catInfo.Seq))
}
}
} else if catInfo.EbaiSyncStatus&model.SyncFlagModifiedMask != 0 { // 修改
err = api.EbaiAPI.ShopCategoryUpdate(strStoreID, catInfo.EbaiID, formatName(catInfo.Name), jxCatSeq2Ebai(catInfo.Seq))
}
}
if err == nil {
db2 := dao.GetDB()
catInfo.EbaiSyncStatus = 0
_, err = dao.UpdateEntity(db2, &catInfo.StoreSkuCategoryMap, updateFields...)
}
return nil, err
}, catList)
rootTask.AddChild(task).Run()
_, err = task.GetResult(0)
}
return nil, err
}, 2)
if err == nil {
db2 := dao.GetDB()
catInfo.EbaiSyncStatus = 0
_, err = dao.UpdateEntity(db2, &catInfo.StoreSkuCategoryMap, updateFields...)
}
return nil, err
}, catList)
rootTask.AddChild(task).Run()
_, err = task.GetResult(0)
}
return nil, err
}, 2)
tasksch.AddChild(parentTask, rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)

View File

@@ -36,7 +36,7 @@ func TestSyncOneStoreCategoriesFromLocal2Remote(t *testing.T) {
}
func TestGetAllRemoteSkus(t *testing.T) {
result, err := new(PurchaseHandler).GetAllRemoteSkus(testShopID)
result, err := new(PurchaseHandler).GetAllRemoteSkus(jxcontext.AdminCtx, testShopID, nil)
if err != nil {
t.Fatal(err.Error())
} else {

View File

@@ -302,44 +302,45 @@ func (p *PurchaseHandler) RefreshAllSkusID(ctx *jxcontext.Context, parentTask ta
var skuPairs []*jdapi.SkuIDPair
const stepCount = 2
rootTask := tasksch.NewSeqTask("jd RefreshAllSkusID", ctx.GetUserName(), func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = dao.GetRows(db, &skuPairs, `
rootTask := tasksch.NewSeqTask("jd RefreshAllSkusID", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = dao.GetRows(db, &skuPairs, `
SELECT t1.id out_sku_id, t1.jd_id sku_id
FROM sku t1
WHERE t1.deleted_at = ?
`, utils.DefaultTimeValue)
default:
taskName := "RefreshAllSkusID update id"
if step != stepCount-1 {
taskName = "RefreshAllSkusID update uuid"
default:
taskName := "RefreshAllSkusID update id"
if step != stepCount-1 {
taskName = "RefreshAllSkusID update uuid"
}
task1 := tasksch.NewParallelTask(taskName, tasksch.NewParallelConfig().SetIsContinueWhenError(true).SetBatchSize(jdapi.MaxBatchSize4BatchUpdateOutSkuId), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
skuPairs := make([]*jdapi.SkuIDPair, len(batchItemList))
for k, v := range batchItemList {
pair := v.(*jdapi.SkuIDPair)
skuPairs[k] = &jdapi.SkuIDPair{
SkuId: pair.SkuId,
OutSkuId: pair.OutSkuId,
}
if step != stepCount-1 {
skuPairs[k].OutSkuId = utils.GetUUID()
}
}
globals.SugarLogger.Debug(utils.Format4Output(skuPairs, false))
if globals.EnableStoreWrite {
_, err = api.JdAPI.BatchUpdateOutSkuId(skuPairs)
}
return nil, err
}, skuPairs)
rootTask.AddChild(task1).Run()
_, err = task1.GetResult(0)
}
task1 := tasksch.NewParallelTask(taskName, tasksch.NewParallelConfig().SetIsContinueWhenError(true).SetBatchSize(jdapi.MaxBatchSize4BatchUpdateOutSkuId), ctx.GetUserName(), func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
skuPairs := make([]*jdapi.SkuIDPair, len(batchItemList))
for k, v := range batchItemList {
pair := v.(*jdapi.SkuIDPair)
skuPairs[k] = &jdapi.SkuIDPair{
SkuId: pair.SkuId,
OutSkuId: pair.OutSkuId,
}
if step != stepCount-1 {
skuPairs[k].OutSkuId = utils.GetUUID()
}
}
globals.SugarLogger.Debug(utils.Format4Output(skuPairs, false))
if globals.EnableStoreWrite {
_, err = api.JdAPI.BatchUpdateOutSkuId(skuPairs)
}
return nil, err
}, skuPairs)
rootTask.AddChild(task1).Run()
_, err = task1.GetResult(0)
}
return nil, err
}, stepCount)
ctx.SetTaskOrAddChild(rootTask, parentTask)
rootTask.Run()
return nil, err
}, stepCount)
tasksch.HandleTask(rootTask, parentTask, false).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
}

View File

@@ -209,41 +209,42 @@ func (p *PurchaseHandler) RefreshAllStoresID(ctx *jxcontext.Context, parentTask
const stepCount = 3
var stores []*tJdStoreInfo
db := dao.GetDB()
rootTask := tasksch.NewSeqTask("jd RefreshAllStoresID", ctx.GetUserName(), func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = dao.GetRows(db, &stores, `
rootTask := tasksch.NewSeqTask("jd RefreshAllStoresID", ctx,
func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = dao.GetRows(db, &stores, `
SELECT t1.*, t2.vendor_store_id
FROM store t1
JOIN store_map t2 ON t1.id = t2.store_id AND t2.deleted_at = ? AND t2.vendor_id = ?
WHERE t1.deleted_at = ?
`, utils.DefaultTimeValue, model.VendorIDJD, utils.DefaultTimeValue)
default:
taskName := "jd RefreshAllStoresID update outSystemId"
if step != stepCount-1 {
taskName = "jd RefreshAllStoresID update to uuid"
}
task1 := tasksch.NewParallelTask(taskName, nil, ctx.GetUserName(), func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
store := batchItemList[0].(*tJdStoreInfo)
storeParams := map[string]interface{}{
"outSystemId": utils.Int2Str(int(store.ID)),
}
default:
taskName := "jd RefreshAllStoresID update outSystemId"
if step != stepCount-1 {
storeParams["outSystemId"] = utils.GetUUID()
taskName = "jd RefreshAllStoresID update to uuid"
}
if true { //globals.EnableStoreWrite {
err = api.JdAPI.UpdateStoreInfo4Open(store.VendorStoreID, ctx.GetUserName(), storeParams)
}
return nil, err
}, stores)
task.AddChild(task1).Run()
_, err = task1.GetResult(0)
}
return nil, err
}, stepCount)
task1 := tasksch.NewParallelTask(taskName, nil, ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
store := batchItemList[0].(*tJdStoreInfo)
storeParams := map[string]interface{}{
"outSystemId": utils.Int2Str(int(store.ID)),
}
if step != stepCount-1 {
storeParams["outSystemId"] = utils.GetUUID()
}
if true { //globals.EnableStoreWrite {
err = api.JdAPI.UpdateStoreInfo4Open(store.VendorStoreID, ctx.GetUserName(), storeParams)
}
return nil, err
}, stores)
task.AddChild(task1).Run()
_, err = task1.GetResult(0)
}
return nil, err
}, stepCount)
ctx.SetTaskOrAddChild(rootTask, parentTask)
rootTask.Run()
tasksch.HandleTask(rootTask, parentTask, false).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
}

View File

@@ -54,106 +54,106 @@ func (p *PurchaseHandler) SyncStoreSkus(ctx *jxcontext.Context, parentTask tasks
if err = dao.GetRows(db, &storeSkus, sql, append(sqlParams, sqlWhereParams...)...); err != nil {
return "", err
}
task := tasksch.NewParallelTask("SyncStoresSkus京东", tasksch.NewParallelConfig().SetBatchSize(jdapi.MaxStoreSkuBatchSize).SetIsContinueWhenError(isContinueWhenError), ctx.GetUserName(), func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
var skuPriceInfoList []*jdapi.SkuPriceInfo
var skuVendibilityList []*jdapi.StockVendibility
var skuStockList []*jdapi.SkuStock
stationNo := batchItemList[0].(*tStoreSkuBindExt).VendorStoreID
var batchSkuIDs []int
for _, v := range batchItemList {
storeSku := v.(*tStoreSkuBindExt)
alreadyAddStock := false
if storeSku.JdSyncStatus&model.SyncFlagChangedMask != 0 {
batchSkuIDs = append(batchSkuIDs, storeSku.SkuID)
if storeSku.JdSyncStatus&(model.SyncFlagDeletedMask|model.SyncFlagNewMask) != 0 { // 关注或取消关注
stock := &jdapi.SkuStock{
OutSkuId: utils.Int2Str(storeSku.SkuID),
StockQty: model.MaxStoreSkuStockQty,
}
if storeSku.DeletedAt != utils.DefaultTimeValue {
stock.StockQty = 0
} else {
alreadyAddStock = true
}
if stock.StockQty != 0 || !storeskulock.IsJdStoreSkuLocked(stationNo, storeSku.JdID) {
skuStockList = append(skuStockList, stock)
}
}
if storeSku.JdSyncStatus&(model.SyncFlagPriceMask|model.SyncFlagNewMask) != 0 {
skuPriceInfoList = append(skuPriceInfoList, &jdapi.SkuPriceInfo{
OutSkuId: utils.Int2Str(storeSku.SkuID),
Price: jxutils.CaculateSkuVendorPrice(storeSku.Price, storeSku.PricePercentage),
})
}
if storeSku.JdSyncStatus&(model.SyncFlagSaleMask|model.SyncFlagNewMask) != 0 {
vendibility := &jdapi.StockVendibility{
OutSkuId: utils.Int2Str(storeSku.SkuID),
DoSale: true,
}
if storeSku.Status != model.StoreSkuBindStatusNormal {
vendibility.DoSale = false
} else if !alreadyAddStock { // 如果是设置可售则自动将库存加满
task := tasksch.NewParallelTask("SyncStoresSkus京东", tasksch.NewParallelConfig().SetBatchSize(jdapi.MaxStoreSkuBatchSize).SetIsContinueWhenError(isContinueWhenError), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
var skuPriceInfoList []*jdapi.SkuPriceInfo
var skuVendibilityList []*jdapi.StockVendibility
var skuStockList []*jdapi.SkuStock
stationNo := batchItemList[0].(*tStoreSkuBindExt).VendorStoreID
var batchSkuIDs []int
for _, v := range batchItemList {
storeSku := v.(*tStoreSkuBindExt)
alreadyAddStock := false
if storeSku.JdSyncStatus&model.SyncFlagChangedMask != 0 {
batchSkuIDs = append(batchSkuIDs, storeSku.SkuID)
if storeSku.JdSyncStatus&(model.SyncFlagDeletedMask|model.SyncFlagNewMask) != 0 { // 关注或取消关注
stock := &jdapi.SkuStock{
OutSkuId: utils.Int2Str(storeSku.SkuID),
StockQty: model.MaxStoreSkuStockQty,
}
skuStockList = append(skuStockList, stock)
if storeSku.DeletedAt != utils.DefaultTimeValue {
stock.StockQty = 0
} else {
alreadyAddStock = true
}
if stock.StockQty != 0 || !storeskulock.IsJdStoreSkuLocked(stationNo, storeSku.JdID) {
skuStockList = append(skuStockList, stock)
}
}
if vendibility.DoSale || !storeskulock.IsJdStoreSkuLocked(stationNo, storeSku.JdID) {
skuVendibilityList = append(skuVendibilityList, vendibility)
if storeSku.JdSyncStatus&(model.SyncFlagPriceMask|model.SyncFlagNewMask) != 0 {
skuPriceInfoList = append(skuPriceInfoList, &jdapi.SkuPriceInfo{
OutSkuId: utils.Int2Str(storeSku.SkuID),
Price: jxutils.CaculateSkuVendorPrice(storeSku.Price, storeSku.PricePercentage),
})
}
if storeSku.JdSyncStatus&(model.SyncFlagSaleMask|model.SyncFlagNewMask) != 0 {
vendibility := &jdapi.StockVendibility{
OutSkuId: utils.Int2Str(storeSku.SkuID),
DoSale: true,
}
if storeSku.Status != model.StoreSkuBindStatusNormal {
vendibility.DoSale = false
} else if !alreadyAddStock { // 如果是设置可售则自动将库存加满
stock := &jdapi.SkuStock{
OutSkuId: utils.Int2Str(storeSku.SkuID),
StockQty: model.MaxStoreSkuStockQty,
}
skuStockList = append(skuStockList, stock)
}
if vendibility.DoSale || !storeskulock.IsJdStoreSkuLocked(stationNo, storeSku.JdID) {
skuVendibilityList = append(skuVendibilityList, vendibility)
}
}
}
}
}
syncMask := 0
errList := []error{}
if globals.EnableStoreWrite {
// todo 以下可以优化为并行操作
globals.SugarLogger.Debug(utils.Format4Output(skuVendibilityList, false), utils.Format4Output(skuPriceInfoList, false), utils.Format4Output(skuStockList, false))
if len(skuVendibilityList) > 0 {
if _, err = api.JdAPI.BatchUpdateVendibility("", stationNo, skuVendibilityList, ctx.GetUserName()); err == nil {
syncMask |= model.SyncFlagSaleMask
} else {
errList = append(errList, err)
syncMask := 0
errList := []error{}
if globals.EnableStoreWrite {
// todo 以下可以优化为并行操作
globals.SugarLogger.Debug(utils.Format4Output(skuVendibilityList, false), utils.Format4Output(skuPriceInfoList, false), utils.Format4Output(skuStockList, false))
if len(skuVendibilityList) > 0 {
if _, err = api.JdAPI.BatchUpdateVendibility("", stationNo, skuVendibilityList, ctx.GetUserName()); err == nil {
syncMask |= model.SyncFlagSaleMask
} else {
errList = append(errList, err)
}
}
if (err == nil || isContinueWhenError) && len(skuStockList) > 0 {
if _, err = api.JdAPI.BatchUpdateCurrentQtys("", stationNo, skuStockList, ctx.GetUserName()); err == nil {
syncMask |= model.SyncFlagNewMask | model.SyncFlagDeletedMask
} else {
errList = append(errList, err)
}
}
if (err == nil || isContinueWhenError) && len(skuPriceInfoList) > 0 {
if _, err = api.JdAPI.UpdateVendorStationPrice("", stationNo, skuPriceInfoList); err == nil {
syncMask |= model.SyncFlagPriceMask
} else {
errList = append(errList, err)
}
}
}
if (err == nil || isContinueWhenError) && len(skuStockList) > 0 {
if _, err = api.JdAPI.BatchUpdateCurrentQtys("", stationNo, skuStockList, ctx.GetUserName()); err == nil {
syncMask |= model.SyncFlagNewMask | model.SyncFlagDeletedMask
} else {
errList = append(errList, err)
}
if len(errList) == 0 {
syncMask = -1
}
if (err == nil || isContinueWhenError) && len(skuPriceInfoList) > 0 {
if _, err = api.JdAPI.UpdateVendorStationPrice("", stationNo, skuPriceInfoList); err == nil {
syncMask |= model.SyncFlagPriceMask
} else {
errList = append(errList, err)
}
}
}
if len(errList) == 0 {
syncMask = -1
}
if syncMask != 0 && len(batchSkuIDs) > 0 {
db := dao.GetDB() // 多线程问题
sql := `
if syncMask != 0 && len(batchSkuIDs) > 0 {
db := dao.GetDB() // 多线程问题
sql := `
UPDATE store_sku_bind t1
SET t1.jd_sync_status = t1.jd_sync_status & ?
` + sqlWhere0 + " AND t1.sku_id IN (" + dao.GenQuestionMarks(len(batchSkuIDs)) + ")"
if _, err = dao.ExecuteSQL(db, sql, ^syncMask, storeID, batchSkuIDs); err != nil {
errList = append(errList, err)
if _, err = dao.ExecuteSQL(db, sql, ^syncMask, storeID, batchSkuIDs); err != nil {
errList = append(errList, err)
}
}
}
if len(errList) == 1 {
err = errList[0]
} else if len(errList) > 1 {
err = fmt.Errorf("%v", errList)
}
return nil, err
}, storeSkus)
ctx.SetTaskOrAddChild(task, parentTask)
task.Run()
if len(errList) == 1 {
err = errList[0]
} else if len(errList) > 1 {
err = fmt.Errorf("%v", errList)
}
return nil, err
}, storeSkus)
tasksch.HandleTask(task, parentTask, false).Run()
if !isAsync {
_, err = task.GetResult(0)
}
@@ -185,83 +185,83 @@ func (p *PurchaseHandler) syncStoreSkus(ctx *jxcontext.Context, parentTask tasks
return "", err
}
stationNo := storeDetail.VendorStoreID
task := tasksch.NewParallelTask("SyncStoresSkus京东", tasksch.NewParallelConfig().SetBatchSize(jdapi.MaxStoreSkuBatchSize).SetIsContinueWhenError(isContinueWhenError), ctx.GetUserName(), func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (interface{}, error) {
var skuPriceInfoList []*jdapi.SkuPriceInfo
var skuVendibilityList []*jdapi.StockVendibility
var skuStockList []*jdapi.SkuStock
var batchSkuIDs []int
for _, v := range batchItemList {
storeSku := v.(*dao.StoreSkuSyncInfo)
alreadyAddStock := false
if storeSku.SkuSyncStatus&model.SyncFlagChangedMask != 0 || storeSku.BindID == 0 {
if storeSku.BindID != 0 {
batchSkuIDs = append(batchSkuIDs, storeSku.BindID)
}
if storeSku.SkuSyncStatus&(model.SyncFlagDeletedMask|model.SyncFlagNewMask) != 0 || storeSku.BindID == 0 { // 关注或取消关注
stock := &jdapi.SkuStock{
OutSkuId: utils.Int2Str(storeSku.ID),
StockQty: model.MaxStoreSkuStockQty,
task := tasksch.NewParallelTask("SyncStoresSkus京东", tasksch.NewParallelConfig().SetBatchSize(jdapi.MaxStoreSkuBatchSize).SetIsContinueWhenError(isContinueWhenError), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (interface{}, error) {
var skuPriceInfoList []*jdapi.SkuPriceInfo
var skuVendibilityList []*jdapi.StockVendibility
var skuStockList []*jdapi.SkuStock
var batchSkuIDs []int
for _, v := range batchItemList {
storeSku := v.(*dao.StoreSkuSyncInfo)
alreadyAddStock := false
if storeSku.SkuSyncStatus&model.SyncFlagChangedMask != 0 || storeSku.BindID == 0 {
if storeSku.BindID != 0 {
batchSkuIDs = append(batchSkuIDs, storeSku.BindID)
}
if storeSku.DeletedAt != utils.DefaultTimeValue || storeSku.BindID == 0 {
stock.StockQty = 0
} else {
alreadyAddStock = true
}
if stock.StockQty != 0 || !storeskulock.IsJdStoreSkuLocked(stationNo, storeSku.JdID) {
skuStockList = append(skuStockList, stock)
}
}
if storeSku.SkuSyncStatus&(model.SyncFlagPriceMask|model.SyncFlagNewMask) != 0 {
skuPriceInfoList = append(skuPriceInfoList, &jdapi.SkuPriceInfo{
OutSkuId: utils.Int2Str(storeSku.ID),
Price: jxutils.CaculateSkuVendorPrice(int(storeSku.Price), int(storeDetail.PricePercentage)),
})
}
if storeSku.SkuSyncStatus&(model.SyncFlagSaleMask|model.SyncFlagNewMask) != 0 {
vendibility := &jdapi.StockVendibility{
OutSkuId: utils.Int2Str(storeSku.ID),
DoSale: true,
}
if storeSku.StoreSkuStatus != model.StoreSkuBindStatusNormal {
vendibility.DoSale = false
} else if !alreadyAddStock { // 如果是设置可售则自动将库存加满
if storeSku.SkuSyncStatus&(model.SyncFlagDeletedMask|model.SyncFlagNewMask) != 0 || storeSku.BindID == 0 { // 关注或取消关注
stock := &jdapi.SkuStock{
OutSkuId: utils.Int2Str(storeSku.ID),
StockQty: model.MaxStoreSkuStockQty,
}
skuStockList = append(skuStockList, stock)
if storeSku.DeletedAt != utils.DefaultTimeValue || storeSku.BindID == 0 {
stock.StockQty = 0
} else {
alreadyAddStock = true
}
if stock.StockQty != 0 || !storeskulock.IsJdStoreSkuLocked(stationNo, storeSku.JdID) {
skuStockList = append(skuStockList, stock)
}
}
if vendibility.DoSale || !storeskulock.IsJdStoreSkuLocked(stationNo, storeSku.JdID) {
skuVendibilityList = append(skuVendibilityList, vendibility)
if storeSku.SkuSyncStatus&(model.SyncFlagPriceMask|model.SyncFlagNewMask) != 0 {
skuPriceInfoList = append(skuPriceInfoList, &jdapi.SkuPriceInfo{
OutSkuId: utils.Int2Str(storeSku.ID),
Price: jxutils.CaculateSkuVendorPrice(int(storeSku.Price), int(storeDetail.PricePercentage)),
})
}
if storeSku.SkuSyncStatus&(model.SyncFlagSaleMask|model.SyncFlagNewMask) != 0 {
vendibility := &jdapi.StockVendibility{
OutSkuId: utils.Int2Str(storeSku.ID),
DoSale: true,
}
if storeSku.StoreSkuStatus != model.StoreSkuBindStatusNormal {
vendibility.DoSale = false
} else if !alreadyAddStock { // 如果是设置可售则自动将库存加满
stock := &jdapi.SkuStock{
OutSkuId: utils.Int2Str(storeSku.ID),
StockQty: model.MaxStoreSkuStockQty,
}
skuStockList = append(skuStockList, stock)
}
if vendibility.DoSale || !storeskulock.IsJdStoreSkuLocked(stationNo, storeSku.JdID) {
skuVendibilityList = append(skuVendibilityList, vendibility)
}
}
}
}
}
globals.SugarLogger.Debugf("jd syncStoreSkus sync detail, storeID:%d, skuVendibilityList:%s, skuPriceInfoList:%s, skuStockList:%s", storeID, utils.Format4Output(skuVendibilityList, true), utils.Format4Output(skuPriceInfoList, true), utils.Format4Output(skuStockList, true))
if globals.EnableStoreWrite {
// todo 以下可以优化为并行操作
if len(skuVendibilityList) > 0 {
_, err = api.JdAPI.BatchUpdateVendibility("", stationNo, skuVendibilityList, ctx.GetUserName())
globals.SugarLogger.Debugf("jd syncStoreSkus sync detail, storeID:%d, skuVendibilityList:%s, skuPriceInfoList:%s, skuStockList:%s", storeID, utils.Format4Output(skuVendibilityList, true), utils.Format4Output(skuPriceInfoList, true), utils.Format4Output(skuStockList, true))
if globals.EnableStoreWrite {
// todo 以下可以优化为并行操作
if len(skuVendibilityList) > 0 {
_, err = api.JdAPI.BatchUpdateVendibility("", stationNo, skuVendibilityList, ctx.GetUserName())
}
if err == nil && len(skuStockList) > 0 {
_, err = api.JdAPI.BatchUpdateCurrentQtys("", stationNo, skuStockList, ctx.GetUserName())
}
if err == nil && len(skuPriceInfoList) > 0 {
_, err = api.JdAPI.UpdateVendorStationPrice("", stationNo, skuPriceInfoList)
}
}
if err == nil && len(skuStockList) > 0 {
_, err = api.JdAPI.BatchUpdateCurrentQtys("", stationNo, skuStockList, ctx.GetUserName())
}
if err == nil && len(skuPriceInfoList) > 0 {
_, err = api.JdAPI.UpdateVendorStationPrice("", stationNo, skuPriceInfoList)
}
}
if err == nil && len(batchSkuIDs) > 0 {
db := dao.GetDB() // 多线程问题
sql := `
if err == nil && len(batchSkuIDs) > 0 {
db := dao.GetDB() // 多线程问题
sql := `
UPDATE store_sku_bind t1
SET t1.jd_sync_status = 0
WHERE t1.id IN (` + dao.GenQuestionMarks(len(batchSkuIDs)) + ")"
_, err = dao.ExecuteSQL(db, sql, batchSkuIDs)
}
return nil, err
}, skus)
ctx.SetTaskOrAddChild(task, parentTask)
task.Run()
_, err = dao.ExecuteSQL(db, sql, batchSkuIDs)
}
return nil, err
}, skus)
tasksch.HandleTask(task, parentTask, false).Run()
if !isAsync {
_, err = task.GetResult(0)
}

View File

@@ -17,7 +17,6 @@ import (
// hint如果是异步返回的是任务ID如果是同步返回是本次需要同步的目录数
func (p *PurchaseHandler) SyncStoreCategory(ctx *jxcontext.Context, parentTask tasksch.ITask, storeID int, isAsync bool) (hint string, err error) {
userName := ctx.GetUserName()
num := 0
db := dao.GetDB()
storeDetail, err := dao.GetStoreDetail(db, storeID, model.VendorIDMTWM)
@@ -25,57 +24,59 @@ func (p *PurchaseHandler) SyncStoreCategory(ctx *jxcontext.Context, parentTask t
return hint, err
}
vendorStoreID := storeDetail.VendorStoreID
rootTask := tasksch.NewSeqTask("美团外卖SyncStoreCategory step1", userName, func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
level := step + 1
catList, err := dao.GetStoreCategories(db, model.VendorIDMTWM, storeID, level)
if len(catList) > 0 {
num += len(catList)
task := tasksch.NewParallelTask(fmt.Sprintf("美团外卖SyncStoreCategory step2, level=%d", level), nil, userName, func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
updateFields := []string{dao.GetSyncStatusStructField(model.VendorNames[model.VendorIDMTWM])}
catInfo := batchItemList[0].(*dao.StoreCatSyncInfo)
if globals.EnableStoreWrite && globals.EnableMtwmStoreWrite {
if catInfo.MtwmSyncStatus&model.SyncFlagDeletedMask != 0 { // 删除
globals.SugarLogger.Debugf("RetailCatDelete vendorStoreID:%s, MtwmID:%s", vendorStoreID, catInfo.MtwmID)
err = api.MtwmAPI.RetailCatDelete(vendorStoreID, catInfo.MtwmID)
} else if catInfo.MtwmSyncStatus&(model.SyncFlagNewMask|model.SyncFlagModifiedMask) != 0 { // 新增
catName := catInfo.CatName
subCatName := ""
originName := ""
if catInfo.MtwmSyncStatus&model.SyncFlagNewMask == 0 {
originName = catInfo.MtwmID
}
if level == 2 {
originName = catInfo.ParentCatName
catName = catInfo.ParentCatName
subCatName = catInfo.CatName
if catInfo.MtwmSyncStatus&model.SyncFlagNewMask == 0 {
originName = catInfo.MtwmID
catName = catInfo.CatName
subCatName = ""
rootTask := tasksch.NewSeqTask("美团外卖SyncStoreCategory step1", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
level := step + 1
catList, err := dao.GetStoreCategories(db, model.VendorIDMTWM, storeID, level)
if len(catList) > 0 {
num += len(catList)
task := tasksch.NewParallelTask(fmt.Sprintf("美团外卖SyncStoreCategory step2, level=%d", level), nil, ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
updateFields := []string{dao.GetSyncStatusStructField(model.VendorNames[model.VendorIDMTWM])}
catInfo := batchItemList[0].(*dao.StoreCatSyncInfo)
if globals.EnableStoreWrite && globals.EnableMtwmStoreWrite {
if catInfo.MtwmSyncStatus&model.SyncFlagDeletedMask != 0 { // 删除
globals.SugarLogger.Debugf("RetailCatDelete vendorStoreID:%s, MtwmID:%s", vendorStoreID, catInfo.MtwmID)
err = api.MtwmAPI.RetailCatDelete(vendorStoreID, catInfo.MtwmID)
} else if catInfo.MtwmSyncStatus&(model.SyncFlagNewMask|model.SyncFlagModifiedMask) != 0 { // 新增
catName := catInfo.CatName
subCatName := ""
originName := ""
if catInfo.MtwmSyncStatus&model.SyncFlagNewMask == 0 {
originName = catInfo.MtwmID
}
if level == 2 {
originName = catInfo.ParentCatName
catName = catInfo.ParentCatName
subCatName = catInfo.CatName
if catInfo.MtwmSyncStatus&model.SyncFlagNewMask == 0 {
originName = catInfo.MtwmID
catName = catInfo.CatName
subCatName = ""
}
}
if catName == "" {
panic("catName is empty")
}
globals.SugarLogger.Debugf("RetailCatUpdate vendorStoreID:%s, originName:%s, catName:%s, subCatName:%s, seq:%d", vendorStoreID, originName, catName, subCatName, catInfo.Seq)
if err = api.MtwmAPI.RetailCatUpdate(vendorStoreID, originName, catName, subCatName, catInfo.Seq); err == nil {
catInfo.MtwmID = catInfo.CatName
updateFields = append(updateFields, dao.GetVendorThingIDStructField(model.VendorNames[model.VendorIDMTWM]))
}
}
}
if catName == "" {
panic("catName is empty")
if err == nil {
db2 := dao.GetDB()
catInfo.MtwmSyncStatus = 0
_, err = dao.UpdateEntity(db2, &catInfo.StoreSkuCategoryMap, updateFields...)
}
globals.SugarLogger.Debugf("RetailCatUpdate vendorStoreID:%s, originName:%s, catName:%s, subCatName:%s, seq:%d", vendorStoreID, originName, catName, subCatName, catInfo.Seq)
if err = api.MtwmAPI.RetailCatUpdate(vendorStoreID, originName, catName, subCatName, catInfo.Seq); err == nil {
catInfo.MtwmID = catInfo.CatName
updateFields = append(updateFields, dao.GetVendorThingIDStructField(model.VendorNames[model.VendorIDMTWM]))
}
}
}
if err == nil {
db2 := dao.GetDB()
catInfo.MtwmSyncStatus = 0
_, err = dao.UpdateEntity(db2, &catInfo.StoreSkuCategoryMap, updateFields...)
}
return nil, err
}, catList)
rootTask.AddChild(task).Run()
_, err = task.GetResult(0)
}
return nil, err
}, 2)
return nil, err
}, catList)
rootTask.AddChild(task).Run()
_, err = task.GetResult(0)
}
return nil, err
}, 2)
tasksch.AddChild(parentTask, rootTask).Run()
if !isAsync {
hint = utils.Int2Str(num)
@@ -235,56 +236,57 @@ func (p *PurchaseHandler) SyncStoreSkus(ctx *jxcontext.Context, parentTask tasks
}
// globals.SugarLogger.Debug(utils.Format4Output(skus, false))
vendorStoreID := storeDetail.VendorStoreID
rootTask := tasksch.NewParallelTask("美团外卖SyncStoreSkus", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx.GetUserName(), func(rootTask *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
foodDataList := make([]map[string]interface{}, len(batchItemList))
// for k, v := range batchItemList {
v := batchItemList[0]
skuItem := v.(*dao.StoreSkuSyncInfo)
if skuItem.SkuSyncStatus&model.SyncFlagDeletedMask != 0 {
err = api.MtwmAPI.RetailDelete(vendorStoreID, utils.Int2Str(skuItem.ID))
} else if skuItem.SkuSyncStatus&(model.SyncFlagModifiedMask|model.SyncFlagNewMask) != 0 {
foodData := make(map[string]interface{})
foodDataList[0] = foodData
foodData[mtwmapi.KeyAppFoodCode] = utils.Int2Str(skuItem.ID)
foodData["name"] = jxutils.ComposeSkuName(skuItem.Prefix, skuItem.Name, skuItem.Comment, skuItem.Unit, skuItem.SpecQuality, skuItem.SpecUnit, 30)
foodData["description"] = skuItem.Comment
foodData["price"] = jxutils.IntPrice2Standard(int64(jxutils.CaculateSkuVendorPrice(int(skuItem.Price), int(storeDetail.PricePercentage))))
foodData["min_order_count"] = 1
foodData["unit"] = skuItem.Unit
foodData["box_num"] = 0
foodData["box_price"] = 0.0
foodData["category_name"] = skuItem.VendorCatID
foodData["is_sold_out"] = skuStatusJX2Mtwm(jxutils.MergeSkuStatus(skuItem.Status, skuItem.StoreSkuStatus))
foodData["picture"] = skuItem.Img
if skuItem.VendorVendorCatID != 0 {
foodData["tag_id"] = utils.Int64ToStr(skuItem.VendorVendorCatID)
} else {
// foodData["tag_id"] = utils.Int64ToStr(defVendorCatID)
rootTask := tasksch.NewParallelTask("美团外卖SyncStoreSkus", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx,
func(rootTask *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
foodDataList := make([]map[string]interface{}, len(batchItemList))
// for k, v := range batchItemList {
v := batchItemList[0]
skuItem := v.(*dao.StoreSkuSyncInfo)
if skuItem.SkuSyncStatus&model.SyncFlagDeletedMask != 0 {
err = api.MtwmAPI.RetailDelete(vendorStoreID, utils.Int2Str(skuItem.ID))
} else if skuItem.SkuSyncStatus&(model.SyncFlagModifiedMask|model.SyncFlagNewMask) != 0 {
foodData := make(map[string]interface{})
foodDataList[0] = foodData
foodData[mtwmapi.KeyAppFoodCode] = utils.Int2Str(skuItem.ID)
foodData["name"] = jxutils.ComposeSkuName(skuItem.Prefix, skuItem.Name, skuItem.Comment, skuItem.Unit, skuItem.SpecQuality, skuItem.SpecUnit, 30)
foodData["description"] = skuItem.Comment
foodData["price"] = jxutils.IntPrice2Standard(int64(jxutils.CaculateSkuVendorPrice(int(skuItem.Price), int(storeDetail.PricePercentage))))
foodData["min_order_count"] = 1
foodData["unit"] = skuItem.Unit
foodData["box_num"] = 0
foodData["box_price"] = 0.0
foodData["category_name"] = skuItem.VendorCatID
foodData["is_sold_out"] = skuStatusJX2Mtwm(jxutils.MergeSkuStatus(skuItem.Status, skuItem.StoreSkuStatus))
foodData["picture"] = skuItem.Img
if skuItem.VendorVendorCatID != 0 {
foodData["tag_id"] = utils.Int64ToStr(skuItem.VendorVendorCatID)
} else {
// foodData["tag_id"] = utils.Int64ToStr(defVendorCatID)
}
skus := []map[string]interface{}{
map[string]interface{}{
"sku_id": foodData[mtwmapi.KeyAppFoodCode],
"spec": jxutils.ComposeSkuSpec(skuItem.SpecQuality, skuItem.SpecUnit),
"price": foodData["price"],
"stock": "*",
"upc": skuItem.Upc,
},
}
if foodData["tag_id"] != nil {
skus[0]["weight"] = skuItem.Weight // weight字段仅限服饰鞋帽、美妆、日用品、母婴、生鲜果蔬、生活超市下的便利店/超市门店品类的商家使用
}
foodData["skus"] = skus
if globals.EnableStoreWrite && globals.EnableMtwmStoreWrite {
err = api.MtwmAPI.RetailBatchInitData(vendorStoreID, foodDataList)
}
}
skus := []map[string]interface{}{
map[string]interface{}{
"sku_id": foodData[mtwmapi.KeyAppFoodCode],
"spec": jxutils.ComposeSkuSpec(skuItem.SpecQuality, skuItem.SpecUnit),
"price": foodData["price"],
"stock": "*",
"upc": skuItem.Upc,
},
if err == nil {
storeSkuBind := &model.StoreSkuBind{}
storeSkuBind.ID = skuItem.BindID
_, err = dao.UpdateEntity(nil, storeSkuBind, model.FieldMtwmSyncStatus)
}
if foodData["tag_id"] != nil {
skus[0]["weight"] = skuItem.Weight // weight字段仅限服饰鞋帽、美妆、日用品、母婴、生鲜果蔬、生活超市下的便利店/超市门店品类的商家使用
}
foodData["skus"] = skus
if globals.EnableStoreWrite && globals.EnableMtwmStoreWrite {
err = api.MtwmAPI.RetailBatchInitData(vendorStoreID, foodDataList)
}
}
if err == nil {
storeSkuBind := &model.StoreSkuBind{}
storeSkuBind.ID = skuItem.BindID
_, err = dao.UpdateEntity(nil, storeSkuBind, model.FieldMtwmSyncStatus)
}
return nil, err
}, skus)
return nil, err
}, skus)
if parentTask != nil {
parentTask.AddChild(rootTask)
}
@@ -307,28 +309,29 @@ func (p *PurchaseHandler) FullSyncStoreSkus(ctx *jxcontext.Context, parentTask t
globals.SugarLogger.Debugf("mtwm FullSyncStoreSkus storeID:%d, isContinueWhenError:%t, userName:%s", storeID, isContinueWhenError, userName)
db := dao.GetDB()
rootTask := tasksch.NewSeqTask("美团外卖FullSyncStoreSkus", userName, func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = p.DeleteRemoteSkus(ctx, rootTask, storeID, nil)
if isContinueWhenError {
err = nil
rootTask := tasksch.NewSeqTask("美团外卖FullSyncStoreSkus", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = p.DeleteRemoteSkus(ctx, rootTask, storeID, nil)
if isContinueWhenError {
err = nil
}
case 1:
_, err = dao.SetStoreSkuSyncStatus(db, model.VendorIDMTWM, storeID, nil, model.SyncFlagNewMask)
case 2:
if err = p.DeleteRemoteCategories(ctx, rootTask, storeID, nil); err == nil {
_, err = dao.SetStoreCategorySyncStatus(db, model.VendorIDMTWM, storeID, nil, model.SyncFlagNewMask)
}
case 3:
_, err = p.SyncLocalStoreCategory(ctx, db, storeID, true)
case 4:
_, err = p.SyncStoreCategory(ctx, rootTask, storeID, false)
case 5:
_, err = p.SyncStoreSkus(ctx, rootTask, storeID, nil, false, isContinueWhenError)
}
case 1:
_, err = dao.SetStoreSkuSyncStatus(db, model.VendorIDMTWM, storeID, nil, model.SyncFlagNewMask)
case 2:
if err = p.DeleteRemoteCategories(ctx, rootTask, storeID, nil); err == nil {
_, err = dao.SetStoreCategorySyncStatus(db, model.VendorIDMTWM, storeID, nil, model.SyncFlagNewMask)
}
case 3:
_, err = p.SyncLocalStoreCategory(ctx, db, storeID, true)
case 4:
_, err = p.SyncStoreCategory(ctx, rootTask, storeID, false)
case 5:
_, err = p.SyncStoreSkus(ctx, rootTask, storeID, nil, false, isContinueWhenError)
}
return nil, err
}, 6)
return nil, err
}, 6)
tasksch.AddChild(parentTask, rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)
@@ -351,13 +354,14 @@ func (p *PurchaseHandler) DeleteRemoteSkus(ctx *jxcontext.Context, parentTask ta
return err
}
vendorStoreID := storeDetail.VendorStoreID
task := tasksch.NewParallelTask("mtwm DeleteRemoteSkus", tasksch.NewParallelConfig().SetIsContinueWhenError(true), "", func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
if globals.EnableStoreWrite && globals.EnableMtwmStoreWrite {
// globals.SugarLogger.Debugf("mtwm RetailDelete vendorStoreID:%s, sku:%s", vendorStoreID, batchItemList[0].(string))
err = api.MtwmAPI.RetailDelete(vendorStoreID, batchItemList[0].(string))
}
return nil, err
}, vendorSkuIDs)
task := tasksch.NewParallelTask("mtwm DeleteRemoteSkus", tasksch.NewParallelConfig().SetIsContinueWhenError(true), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
if globals.EnableStoreWrite && globals.EnableMtwmStoreWrite {
// globals.SugarLogger.Debugf("mtwm RetailDelete vendorStoreID:%s, sku:%s", vendorStoreID, batchItemList[0].(string))
err = api.MtwmAPI.RetailDelete(vendorStoreID, batchItemList[0].(string))
}
return nil, err
}, vendorSkuIDs)
tasksch.AddChild(parentTask, task).Run()
_, err = task.GetResult(0)
return err
@@ -402,25 +406,27 @@ func (p *PurchaseHandler) DeleteRemoteCategories(ctx *jxcontext.Context, parentT
}
}
}
rootTask := tasksch.NewSeqTask("mtwm DeleteRemoteCategories", "", func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
var catIDs []string
if step == 0 {
catIDs = vendorCatIDs2
} else {
catIDs = vendorCatIDs
}
if len(catIDs) > 0 {
task := tasksch.NewParallelTask("mtwm DeleteRemoteCategories paralle", tasksch.NewParallelConfig().SetIsContinueWhenError(true), "", func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
if globals.EnableStoreWrite && globals.EnableMtwmStoreWrite {
err = api.MtwmAPI.RetailCatDelete(vendorStoreID, batchItemList[0].(string))
}
return nil, err
}, catIDs)
rootTask.AddChild(task).Run()
_, err = task.GetResult(0)
}
return nil, err
}, 2)
rootTask := tasksch.NewSeqTask("mtwm DeleteRemoteCategories", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
var catIDs []string
if step == 0 {
catIDs = vendorCatIDs2
} else {
catIDs = vendorCatIDs
}
if len(catIDs) > 0 {
task := tasksch.NewParallelTask("mtwm DeleteRemoteCategories paralle", tasksch.NewParallelConfig().SetIsContinueWhenError(true), ctx,
func(t *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
if globals.EnableStoreWrite && globals.EnableMtwmStoreWrite {
err = api.MtwmAPI.RetailCatDelete(vendorStoreID, batchItemList[0].(string))
}
return nil, err
}, catIDs)
rootTask.AddChild(task).Run()
_, err = task.GetResult(0)
}
return nil, err
}, 2)
tasksch.AddChild(parentTask, rootTask).Run()
_, err = rootTask.GetResult(0)
return err
@@ -432,24 +438,25 @@ func (p *PurchaseHandler) DeleteRemoteStoreSkus(ctx *jxcontext.Context, parentTa
db := dao.GetDB()
var errDeleteSku error
rootTask := tasksch.NewSeqTask("mtwm DeleteRemoteStoreSkus", userName, func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = p.DeleteRemoteSkus(ctx, rootTask, storeID, nil)
errDeleteSku = err
// 强制忽略删除SKU错误
if isContinueWhenError {
err = nil
rootTask := tasksch.NewSeqTask("mtwm DeleteRemoteStoreSkus", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
err = p.DeleteRemoteSkus(ctx, rootTask, storeID, nil)
errDeleteSku = err
// 强制忽略删除SKU错误
if isContinueWhenError {
err = nil
}
case 1:
_, err = dao.SetStoreSkuSyncStatus(db, model.VendorIDMTWM, storeID, nil, model.SyncFlagNewMask)
case 2:
if err = p.DeleteRemoteCategories(ctx, rootTask, storeID, nil); err == nil {
_, err = dao.SetStoreCategorySyncStatus(db, model.VendorIDMTWM, storeID, nil, model.SyncFlagNewMask)
}
}
case 1:
_, err = dao.SetStoreSkuSyncStatus(db, model.VendorIDMTWM, storeID, nil, model.SyncFlagNewMask)
case 2:
if err = p.DeleteRemoteCategories(ctx, rootTask, storeID, nil); err == nil {
_, err = dao.SetStoreCategorySyncStatus(db, model.VendorIDMTWM, storeID, nil, model.SyncFlagNewMask)
}
}
return nil, err
}, 3)
return nil, err
}, 3)
tasksch.AddChild(parentTask, rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)

View File

@@ -24,47 +24,48 @@ const (
)
func (p *PurchaseHandler) SyncStoreCategory(ctx *jxcontext.Context, parentTask tasksch.ITask, storeID int, isAsync bool) (hint string, err error) {
userName := ctx.GetUserName()
strStoreID := utils.Int2Str(storeID)
num := 0
db := dao.GetDB()
rootTask := tasksch.NewSeqTask("微盟微商城SyncStoreCategory step1", userName, func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
level := step + 1
catList, err := dao.GetStoreCategories(db, model.VendorIDWSC, storeID, level)
// globals.SugarLogger.Debug(utils.Format4Output(catList, false))
if len(catList) > 0 {
num += len(catList)
task := tasksch.NewParallelTask(fmt.Sprintf("微盟微商城SyncStoreCategory step2, level=%d", level), nil, userName, func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
updateFields := []string{dao.GetSyncStatusStructField(model.VendorNames[model.VendorIDWSC])}
catInfo := batchItemList[0].(*dao.StoreCatSyncInfo)
if globals.EnableStoreWrite && globals.EnableWscStoreWrite {
if catInfo.WscSyncStatus&model.SyncFlagDeletedMask != 0 { // 删除
globals.SugarLogger.Debugf("UpdateClassify strStoreID:%s, WscID:%d", strStoreID, catInfo.WscID)
err = api.WeimobAPI.UpdateClassify(catInfo.WscID, composeFakeDelName(catInfo.CatName), "")
} else if catInfo.WscSyncStatus&(model.SyncFlagNewMask|model.SyncFlagModifiedMask) != 0 { // 新增
catImg := ""
if level == 2 {
catImg = DefCatImg
rootTask := tasksch.NewSeqTask("微盟微商城SyncStoreCategory step1", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
level := step + 1
catList, err := dao.GetStoreCategories(db, model.VendorIDWSC, storeID, level)
// globals.SugarLogger.Debug(utils.Format4Output(catList, false))
if len(catList) > 0 {
num += len(catList)
task := tasksch.NewParallelTask(fmt.Sprintf("微盟微商城SyncStoreCategory step2, level=%d", level), nil, ctx,
func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
updateFields := []string{dao.GetSyncStatusStructField(model.VendorNames[model.VendorIDWSC])}
catInfo := batchItemList[0].(*dao.StoreCatSyncInfo)
if globals.EnableStoreWrite && globals.EnableWscStoreWrite {
if catInfo.WscSyncStatus&model.SyncFlagDeletedMask != 0 { // 删除
globals.SugarLogger.Debugf("UpdateClassify strStoreID:%s, WscID:%d", strStoreID, catInfo.WscID)
err = api.WeimobAPI.UpdateClassify(catInfo.WscID, composeFakeDelName(catInfo.CatName), "")
} else if catInfo.WscSyncStatus&(model.SyncFlagNewMask|model.SyncFlagModifiedMask) != 0 { // 新增
catImg := ""
if level == 2 {
catImg = DefCatImg
}
if catInfo.WscID, err = api.WeimobAPI.AddClassify(catInfo.CatName, utils.Str2Int64WithDefault(catInfo.ParentVendorCatID, 0), catImg); err == nil {
updateFields = append(updateFields, dao.GetVendorThingIDStructField(model.VendorNames[model.VendorIDWSC]))
}
} else if catInfo.WscSyncStatus&(model.SyncFlagModifiedMask|model.SyncFlagModifiedMask) != 0 { // 修改
err = api.WeimobAPI.UpdateClassify(catInfo.WscID, catInfo.CatName, "")
}
}
if catInfo.WscID, err = api.WeimobAPI.AddClassify(catInfo.CatName, utils.Str2Int64WithDefault(catInfo.ParentVendorCatID, 0), catImg); err == nil {
updateFields = append(updateFields, dao.GetVendorThingIDStructField(model.VendorNames[model.VendorIDWSC]))
if err == nil {
db2 := dao.GetDB()
catInfo.WscSyncStatus = 0
_, err = dao.UpdateEntity(db2, &catInfo.StoreSkuCategoryMap, updateFields...)
}
} else if catInfo.WscSyncStatus&(model.SyncFlagModifiedMask|model.SyncFlagModifiedMask) != 0 { // 修改
err = api.WeimobAPI.UpdateClassify(catInfo.WscID, catInfo.CatName, "")
}
}
if err == nil {
db2 := dao.GetDB()
catInfo.WscSyncStatus = 0
_, err = dao.UpdateEntity(db2, &catInfo.StoreSkuCategoryMap, updateFields...)
}
return nil, err
}, catList)
rootTask.AddChild(task).Run()
_, err = task.GetResult(0)
}
return nil, err
}, 2)
return nil, err
}, catList)
rootTask.AddChild(task).Run()
_, err = task.GetResult(0)
}
return nil, err
}, 2)
tasksch.AddChild(parentTask, rootTask).Run()
if !isAsync {
hint = utils.Int2Str(num)
@@ -170,80 +171,81 @@ func (p *PurchaseHandler) SyncStoreSkus(ctx *jxcontext.Context, parentTask tasks
return "", err
}
globals.SugarLogger.Debug(utils.Format4Output(skus, false))
rootTask := tasksch.NewParallelTask("微盟微商城SyncStoreSkus", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx.GetUserName(), func(rootTask *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
v := batchItemList[0]
skuItem := v.(*dao.StoreSkuSyncInfo)
updateFields := []string{model.FieldWscSyncStatus}
storeSkuBind := &model.StoreSkuBind{}
storeSkuBind.ID = skuItem.BindID
if skuItem.SkuSyncStatus&model.SyncFlagDeletedMask != 0 {
goodsID := utils.Str2Int64WithDefault(skuItem.VendorNameID, 0)
if err = api.WeimobAPI.UpdateGoodsShelfStatus([]int64{goodsID}, false); err == nil {
err = api.WeimobAPI.UpdateGoodsTitle(goodsID, composeFakeDelName(skuItem.Name))
}
} else if skuItem.SkuSyncStatus&(model.SyncFlagModifiedMask|model.SyncFlagNewMask) != 0 {
outerGoodsCode := utils.Int2Str(skuItem.NameID)
title := jxutils.ComposeSkuName(skuItem.Prefix, skuItem.Name, skuItem.Comment, skuItem.Unit, skuItem.SpecQuality, skuItem.SpecUnit, 30)
isPutAway := jxutils.MergeSkuStatus(skuItem.Status, skuItem.StoreSkuStatus) == model.SkuStatusNormal
categoryId := skuItem.VendorVendorCatID
if categoryId == 0 {
categoryId = DefVendorCategoryId
}
classifyIdList := []int64{utils.Str2Int64WithDefault(skuItem.VendorCatID, 0)}
if skuItem.SkuVendorCatID != "" {
if int64Value := utils.Str2Int64WithDefault(skuItem.SkuVendorCatID, 0); int64Value > 0 {
classifyIdList = append(classifyIdList, int64Value)
rootTask := tasksch.NewParallelTask("微盟微商城SyncStoreSkus", tasksch.NewParallelConfig().SetIsContinueWhenError(isContinueWhenError), ctx,
func(rootTask *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) {
v := batchItemList[0]
skuItem := v.(*dao.StoreSkuSyncInfo)
updateFields := []string{model.FieldWscSyncStatus}
storeSkuBind := &model.StoreSkuBind{}
storeSkuBind.ID = skuItem.BindID
if skuItem.SkuSyncStatus&model.SyncFlagDeletedMask != 0 {
goodsID := utils.Str2Int64WithDefault(skuItem.VendorNameID, 0)
if err = api.WeimobAPI.UpdateGoodsShelfStatus([]int64{goodsID}, false); err == nil {
err = api.WeimobAPI.UpdateGoodsTitle(goodsID, composeFakeDelName(skuItem.Name))
}
}
b2cGoods := &weimobapi.PendingSaveB2CGoodsVo{
FreightTemplateId: DefFreightTemplateId,
DeliveryTypeIdList: []int64{DefDeliveryTypeId},
B2cGoodsType: weimobapi.GoodsTypeNormal,
}
salePrice := int64(jxutils.CaculateSkuVendorPrice(int(skuItem.Price), int(storeDetail.PricePercentage)))
skuList := []map[string]interface{}{
map[string]interface{}{
weimobapi.KeyOuterSkuCode: utils.Int2Str(skuItem.ID),
weimobapi.KeyImageURL: skuItem.Img,
weimobapi.KeySalePrice: jxutils.IntPrice2Standard(salePrice),
weimobapi.KeyCostPrice: jxutils.IntPrice2Standard(salePrice * 8 / 10),
weimobapi.KeyOriginalPrice: jxutils.IntPrice2Standard(salePrice * 10 / (6 + rand.Int63n(4))),
weimobapi.KeyEditStockNum: model.MaxStoreSkuStockQty,
weimobapi.KeyB2cSku: &weimobapi.PendingSaveB2CSkuVo{
Weight: jxutils.IntWeight2Float(skuItem.Weight),
} else if skuItem.SkuSyncStatus&(model.SyncFlagModifiedMask|model.SyncFlagNewMask) != 0 {
outerGoodsCode := utils.Int2Str(skuItem.NameID)
title := jxutils.ComposeSkuName(skuItem.Prefix, skuItem.Name, skuItem.Comment, skuItem.Unit, skuItem.SpecQuality, skuItem.SpecUnit, 30)
isPutAway := jxutils.MergeSkuStatus(skuItem.Status, skuItem.StoreSkuStatus) == model.SkuStatusNormal
categoryId := skuItem.VendorVendorCatID
if categoryId == 0 {
categoryId = DefVendorCategoryId
}
classifyIdList := []int64{utils.Str2Int64WithDefault(skuItem.VendorCatID, 0)}
if skuItem.SkuVendorCatID != "" {
if int64Value := utils.Str2Int64WithDefault(skuItem.SkuVendorCatID, 0); int64Value > 0 {
classifyIdList = append(classifyIdList, int64Value)
}
}
b2cGoods := &weimobapi.PendingSaveB2CGoodsVo{
FreightTemplateId: DefFreightTemplateId,
DeliveryTypeIdList: []int64{DefDeliveryTypeId},
B2cGoodsType: weimobapi.GoodsTypeNormal,
}
salePrice := int64(jxutils.CaculateSkuVendorPrice(int(skuItem.Price), int(storeDetail.PricePercentage)))
skuList := []map[string]interface{}{
map[string]interface{}{
weimobapi.KeyOuterSkuCode: utils.Int2Str(skuItem.ID),
weimobapi.KeyImageURL: skuItem.Img,
weimobapi.KeySalePrice: jxutils.IntPrice2Standard(salePrice),
weimobapi.KeyCostPrice: jxutils.IntPrice2Standard(salePrice * 8 / 10),
weimobapi.KeyOriginalPrice: jxutils.IntPrice2Standard(salePrice * 10 / (6 + rand.Int63n(4))),
weimobapi.KeyEditStockNum: model.MaxStoreSkuStockQty,
weimobapi.KeyB2cSku: &weimobapi.PendingSaveB2CSkuVo{
Weight: jxutils.IntWeight2Float(skuItem.Weight),
},
},
},
}
if globals.EnableStoreWrite && globals.EnableWscStoreWrite {
if skuItem.SkuSyncStatus&model.SyncFlagNewMask != 0 {
goodsID, skuMap, err2 := api.WeimobAPI.AddGoods(outerGoodsCode, title, false, []string{skuItem.Img}, skuItem.Comment, isPutAway, 0, categoryId, classifyIdList, b2cGoods, skuList, nil)
if err = err2; err == nil {
storeSkuBind.WscID = skuMap[utils.Int2Str(skuItem.ID)]
storeSkuBind.WscID2 = goodsID
updateFields = append(updateFields, model.FieldWscID, model.FieldWscID2)
}
} else {
goodsID := utils.Str2Int64WithDefault(skuItem.VendorNameID, 0)
goodsInfo, err2 := api.WeimobAPI.QueryGoodsDetail(goodsID)
if err = err2; err == nil {
// http://open.weimob.com/docapi/article?tag=Af
// sku id如果为空则新增sku 如果更新之前的skuId与入参skuId对应则更新sku 如果更新之前的skuId没有和入参的skuId对应删除更新之前的sku
skuList[0][weimobapi.KeySkuID] = utils.Str2Int64WithDefault(skuItem.VendorSkuID, 0)
remoteSkuList := goodsInfo[weimobapi.KeySkuList].([]interface{})
if len(remoteSkuList) > 0 {
skuList[0][weimobapi.KeyEditStockNum] = model.MaxStoreSkuStockQty - int(utils.MustInterface2Int64(remoteSkuList[0].(map[string]interface{})[weimobapi.KeyAvailableStockNum]))
}
if globals.EnableStoreWrite && globals.EnableWscStoreWrite {
if skuItem.SkuSyncStatus&model.SyncFlagNewMask != 0 {
goodsID, skuMap, err2 := api.WeimobAPI.AddGoods(outerGoodsCode, title, false, []string{skuItem.Img}, skuItem.Comment, isPutAway, 0, categoryId, classifyIdList, b2cGoods, skuList, nil)
if err = err2; err == nil {
storeSkuBind.WscID = skuMap[utils.Int2Str(skuItem.ID)]
storeSkuBind.WscID2 = goodsID
updateFields = append(updateFields, model.FieldWscID, model.FieldWscID2)
}
} else {
goodsID := utils.Str2Int64WithDefault(skuItem.VendorNameID, 0)
goodsInfo, err2 := api.WeimobAPI.QueryGoodsDetail(goodsID)
if err = err2; err == nil {
// http://open.weimob.com/docapi/article?tag=Af
// sku id如果为空则新增sku 如果更新之前的skuId与入参skuId对应则更新sku 如果更新之前的skuId没有和入参的skuId对应删除更新之前的sku
skuList[0][weimobapi.KeySkuID] = utils.Str2Int64WithDefault(skuItem.VendorSkuID, 0)
remoteSkuList := goodsInfo[weimobapi.KeySkuList].([]interface{})
if len(remoteSkuList) > 0 {
skuList[0][weimobapi.KeyEditStockNum] = model.MaxStoreSkuStockQty - int(utils.MustInterface2Int64(remoteSkuList[0].(map[string]interface{})[weimobapi.KeyAvailableStockNum]))
}
_, _, err = api.WeimobAPI.UpdateGoods(goodsID, title, false, []string{skuItem.Img}, skuItem.Comment, isPutAway, 0, categoryId, classifyIdList, b2cGoods, skuList, nil)
}
_, _, err = api.WeimobAPI.UpdateGoods(goodsID, title, false, []string{skuItem.Img}, skuItem.Comment, isPutAway, 0, categoryId, classifyIdList, b2cGoods, skuList, nil)
}
}
}
}
if err == nil {
_, err = dao.UpdateEntity(nil, storeSkuBind, updateFields...)
}
return nil, err
}, skus)
if err == nil {
_, err = dao.UpdateEntity(nil, storeSkuBind, updateFields...)
}
return nil, err
}, skus)
if parentTask != nil {
parentTask.AddChild(rootTask)
}
@@ -266,21 +268,22 @@ func (p *PurchaseHandler) FullSyncStoreSkus(ctx *jxcontext.Context, parentTask t
globals.SugarLogger.Debugf("wsc FullSyncStoreSkus storeID:%d, isContinueWhenError:%t, userName:%s", storeID, isContinueWhenError, userName)
db := dao.GetDB()
rootTask := tasksch.NewSeqTask("微盟微商城FullSyncStoreSkus", userName, func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
_, err = dao.SetStoreCategorySyncStatus(db, model.VendorIDWSC, storeID, nil, model.SyncFlagNewMask)
case 1:
_, err = dao.SetStoreSkuSyncStatus(db, model.VendorIDWSC, storeID, nil, model.SyncFlagNewMask)
case 2:
_, err = p.SyncLocalStoreCategory(ctx, db, storeID, false)
case 3:
_, err = p.SyncStoreCategory(ctx, rootTask, storeID, false)
case 4:
_, err = p.SyncStoreSkus(ctx, rootTask, storeID, nil, true, isContinueWhenError)
}
return nil, err
}, 5)
rootTask := tasksch.NewSeqTask("微盟微商城FullSyncStoreSkus", ctx,
func(rootTask *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) {
switch step {
case 0:
_, err = dao.SetStoreCategorySyncStatus(db, model.VendorIDWSC, storeID, nil, model.SyncFlagNewMask)
case 1:
_, err = dao.SetStoreSkuSyncStatus(db, model.VendorIDWSC, storeID, nil, model.SyncFlagNewMask)
case 2:
_, err = p.SyncLocalStoreCategory(ctx, db, storeID, false)
case 3:
_, err = p.SyncStoreCategory(ctx, rootTask, storeID, false)
case 4:
_, err = p.SyncStoreSkus(ctx, rootTask, storeID, nil, true, isContinueWhenError)
}
return nil, err
}, 5)
tasksch.AddChild(parentTask, rootTask).Run()
if !isAsync {
_, err = rootTask.GetResult(0)

View File

@@ -54,6 +54,7 @@ weimobCallbackURL = "http://callback.test.jxc4.com/weimob"
weixinPageAppID = "wx018dbe7daa3d5627"
weixinPageSecret = "c7a84ed3ef3ae04ac78e02fb593ffbe5"
dingdingAgentID = 241047291
dingdingAppKey = "dingpx4hcf55zb4ubewg"
dingdingSecret = "1zooB4bmEXPesdwb1ElWASVQ1vinOSZM-1XCUFrrSjHsNAId1UuVCT5tmHSmg5_V"
@@ -123,6 +124,7 @@ enableWscStoreWrite = true
weimobCallbackURL = "http://callback.jxc4.com/weimob"
dingdingAgentID = 239461075
dingdingAppKey = "ding7iu9cptairtcls0c"
dingdingSecret = "LWrZAFeqUfuVv7n_tc8vPpCAx6PT4CwManx2XCVhJOqGsx2L5XCDuX1sAN_JtvsI"

View File

@@ -90,7 +90,7 @@ func Init() {
weimobAPIConfig.ClientTimeout = 120 * time.Second
WeimobAPI = weimobapi.New(nil, beego.AppConfig.DefaultString("weimobAppID", ""), beego.AppConfig.DefaultString("weimobAppSecret", ""), &weimobAPIConfig)
DingDingAPI = dingdingapi.New(beego.AppConfig.DefaultString("dingdingCorpID", ""), beego.AppConfig.DefaultString("dingdingAppKey", ""), beego.AppConfig.DefaultString("dingdingSecret", ""))
DingDingAPI = dingdingapi.NewWithAgentID(beego.AppConfig.DefaultInt64("dingdingAgentID", 0), beego.AppConfig.DefaultString("dingdingCorpID", ""), beego.AppConfig.DefaultString("dingdingAppKey", ""), beego.AppConfig.DefaultString("dingdingSecret", ""))
DingDingQRCodeAPI = dingdingapi.New(beego.AppConfig.DefaultString("dingdingCorpID", ""), beego.AppConfig.DefaultString("dingdingQRCodeAppKey", ""), beego.AppConfig.DefaultString("dingdingQRCodeSecret", ""))
}