From ac16fa741b23b82d38d086e29e7511f084ad0a34 Mon Sep 17 00:00:00 2001 From: gazebo Date: Tue, 23 Apr 2019 11:50:32 +0800 Subject: [PATCH] =?UTF-8?q?!=20=E4=B8=8D=E7=BC=93=E5=AD=98=E8=AE=A2?= =?UTF-8?q?=E5=8D=95=EF=BC=8C=E6=AF=8F=E6=AC=A1=E8=AE=A2=E5=8D=95=E6=88=96?= =?UTF-8?q?=E8=BF=90=E5=8D=95=E4=BA=8B=E4=BB=B6=E6=97=B6=E9=83=BD=E5=AE=9E?= =?UTF-8?q?=E6=97=B6=E5=8A=A0=E8=BD=BD=E8=AE=A2=E5=8D=95=EF=BC=8C=E7=8A=B6?= =?UTF-8?q?=E6=80=81=E5=8F=98=E5=8C=96=E7=AB=8B=E5=8D=B3=E5=AD=98=E5=82=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- business/jxcallback/orderman/order.go | 4 +- .../jxcallback/scheduler/basesch/basesch.go | 2 + .../jxcallback/scheduler/defsch/defsch.go | 71 +++++++++---------- business/model/order.go | 6 +- 4 files changed, 42 insertions(+), 41 deletions(-) diff --git a/business/jxcallback/orderman/order.go b/business/jxcallback/orderman/order.go index 81183c367..05e756dc7 100644 --- a/business/jxcallback/orderman/order.go +++ b/business/jxcallback/orderman/order.go @@ -376,7 +376,7 @@ func (c *OrderManager) addOrderStatus(orderStatus *model.OrderStatus, db *dao.Da updateFields = append(updateFields, "LockStatus") } } - orderStatus.LockStatus = order.LockStatus + // orderStatus.LockStatus = order.LockStatus if model.IsOrderFinalStatus(orderStatus.Status) { order.OrderFinishedAt = orderStatus.StatusTime updateFields = append(updateFields, "OrderFinishedAt") @@ -389,7 +389,7 @@ func (c *OrderManager) addOrderStatus(orderStatus *model.OrderStatus, db *dao.Da isDuplicated = true } } else { - if err == orm.ErrNoRows { // todo 消息错序 + if dao.IsNoRowsError(err) { // todo 消息错序 err = nil } else { globals.SugarLogger.Warnf("addOrderStatus orderID:%s read failed with error:%v", order.VendorOrderID, err) diff --git a/business/jxcallback/scheduler/basesch/basesch.go b/business/jxcallback/scheduler/basesch/basesch.go index e2ac1ebbc..67d3965bd 100644 --- a/business/jxcallback/scheduler/basesch/basesch.go +++ b/business/jxcallback/scheduler/basesch/basesch.go @@ -62,6 +62,7 @@ func (c *BaseScheduler) Swtich2SelfDeliver(order *model.GoodsOrder, userName str if err == nil { // 因为有些平台转自送后,不会再发送订单在配送中消息过来,所以成功后就强制设置状态为配送中 order.Status = model.OrderStatusDelivering order.DeliveryFlag |= model.OrderDeliveryFlagMaskPurcahseDisabled + err = partner.CurOrderManager.UpdateOrderStatusAndFlag(order) } } } else { @@ -105,6 +106,7 @@ func (c *BaseScheduler) SelfDeliverDelivering(order *model.GoodsOrder, userName }, "SelfDeliverDelivering orderID:%s", order.VendorOrderID) if err == nil { // 因为有些平台设置配送中后,不会发送订单在配送中消息过来,所以成功后就强制设置状态为配送中 order.Status = model.OrderStatusDelivering + err = partner.CurOrderManager.UpdateOrderStatusAndFlag(order) } } } else { diff --git a/business/jxcallback/scheduler/defsch/defsch.go b/business/jxcallback/scheduler/defsch/defsch.go index 7aca915dd..4adb3d0b4 100644 --- a/business/jxcallback/scheduler/defsch/defsch.go +++ b/business/jxcallback/scheduler/defsch/defsch.go @@ -55,9 +55,10 @@ var ( ) type WatchOrderInfo struct { + order *model.GoodsOrder // order里的信息是保持更新的 + autoPickupTimeoutMinute int // 0表示禁用,1表示用缺省值time2AutoPickupMin,其它表示分钟数 storeDeliveryType int - order *model.GoodsOrder // order里的信息是保持更新的 waybills map[int]*model.Waybill // 这个waybills里的状态信息是不真实的,只使用id相关的信息 timerStatusType int // 0表示订单,1表示运单 @@ -112,10 +113,10 @@ func (s *WatchOrderInfo) updateOrderStoreFeature(order *model.GoodsOrder) (err e } s.autoPickupTimeoutMinute = int(storeMap.AutoPickup) s.storeDeliveryType = FixedScheduler.GetStoreDeliveryType(order, storeMap) - if s.storeDeliveryType == scheduler.StoreDeliveryTypeByStore { + if s.storeDeliveryType == scheduler.StoreDeliveryTypeByStore && (order.DeliveryFlag&model.OrderDeliveryFlagMaskPurcahseDisabled) == 0 { order.DeliveryFlag |= model.OrderDeliveryFlagMaskPurcahseDisabled + err = partner.CurOrderManager.UpdateOrderStatusAndFlag(order) } - _, err = dao.UpdateEntity(db, order, "DeliveryFlag") globals.SugarLogger.Debugf("updateOrderStoreFeature orderID:%s, s.storeDeliveryType:%d, order.DeliveryFlag:%d", order.VendorOrderID, s.storeDeliveryType, order.DeliveryFlag) } return err @@ -221,12 +222,7 @@ func Init() { func (s *DefScheduler) OnOrderNew(order *model.GoodsOrder, isPending bool) (err error) { globals.SugarLogger.Debugf("OnOrderNew orderID:%s", order.VendorOrderID) savedOrderInfo := s.loadSavedOrderFromMap(model.Order2Status(order), false) - if savedOrderInfo == nil { - savedOrderInfo = NewWatchOrderInfo(order) - s.orderMap.StoreWithTimeout(jxutils.ComposeUniversalOrderID(order.VendorOrderID, order.VendorID), savedOrderInfo, orderMapStoreMaxTime) - } else { - savedOrderInfo.SetOrder(order) // 调整单或消息错序都可能进到这里来 - } + savedOrderInfo.SetOrder(order) if order.Status >= model.OrderStatusNew { s.resetTimer(savedOrderInfo, nil, isPending) if !isPending && order.Status >= model.OrderStatusAccepted { // 有订单消息错序,先收到接单消息,再收到新订单消息,导致接单TIMER不动作,这里补一下 @@ -242,13 +238,15 @@ func (s *DefScheduler) OnOrderNew(order *model.GoodsOrder, isPending bool) (err // todo 这个接口应该可以直接传order的,因为在OrderManager中每次都生成了 func (s *DefScheduler) OnOrderStatusChanged(order *model.GoodsOrder, status *model.OrderStatus, isPending bool) (err error) { - if order == nil && (status.Status != model.OrderStatusUnknown && status.Status != model.OrderStatusMsg) { - globals.SugarLogger.Warnf("OnOrderStatusChanged order is nil, status:%s", utils.Format4Output(status, true)) - } - if status.LockStatus != model.OrderStatusUnknown || (status.Status > model.OrderStatusMsg && status.Status != model.OrderStatusUnknown) { + if status.Status > model.OrderStatusMsg && status.Status != model.OrderStatusUnknown { globals.SugarLogger.Debugf("OnOrderStatusChanged orderID:%s %s, status:%v", status.VendorOrderID, model.OrderStatusName[status.Status], status) - savedOrderInfo := s.loadSavedOrderFromMap(status, true) - s.updateOrderByStatus(savedOrderInfo.order, status) + if order == nil { + globals.SugarLogger.Warnf("OnOrderStatusChanged order is nil, status:%s", utils.Format4Output(status, true)) + } + savedOrderInfo := s.loadSavedOrderFromMap(status, false) + savedOrderInfo.SetOrder(order) + // s.updateOrderByStatus(savedOrderInfo.order, status) + // if status.Status == model.OrderStatusNew { // if !isPending { // utils.CallFuncAsync(func() { @@ -256,7 +254,11 @@ func (s *DefScheduler) OnOrderStatusChanged(order *model.GoodsOrder, status *mod // }) // } // } - if status.LockStatus == model.OrderStatusUnknown && status.Status > model.OrderStatusUnknown { // 只处理状态转换,一般消息不处理 + if order.LockStatus == model.OrderStatusUnknown && (status.Status > model.OrderStatusUnknown || status.Status == model.OrderStatusRefuseFailedGetGoods) { // 只处理状态转换,一般消息不处理 + if status.Status == model.OrderStatusRefuseFailedGetGoods && order.Status != model.OrderStatusFinishedPickup && !model.IsOrderFinalStatus(order.Status) { + order.Status = model.OrderStatusFinishedPickup + partner.CurOrderManager.UpdateOrderStatusAndFlag(order) + } s.resetTimer(savedOrderInfo, nil, isPending) if status.Status >= model.OrderStatusDelivering { // 会出现创建运单后,门店自己转自送了(例如:828400083000222),当前逻辑会导致此运单不会被取消,有三个可能的修改方法,考虑1: @@ -276,17 +278,16 @@ func (s *DefScheduler) OnOrderStatusChanged(order *model.GoodsOrder, status *mod if status.Status >= model.OrderStatusEndBegin { s.orderMap.Delete(jxutils.GetUniversalOrderIDFromOrderStatus(status)) } - } else if status.Status == model.OrderStatusRefuseFailedGetGoods { - // 将order状态设置为OrderStatusFinishedPickup } } - if status.LockStatus != model.OrderStatusUnknown { + if order.LockStatus != model.OrderStatusUnknown { s.stopTimer(savedOrderInfo) } if model.IsOrderLockStatus(status.Status) || model.IsOrderUnlockStatus(status.Status) || status.Status == model.OrderStatusApplyFailedGetGoods || - status.Status == model.OrderStatusAgreeFailedGetGoods { + status.Status == model.OrderStatusAgreeFailedGetGoods || + status.Status == model.OrderStatusDeliverFailed { if isPending { if status.Status == model.OrderStatusApplyCancel { utils.CallFuncAsync(func() { @@ -592,7 +593,6 @@ func (s *DefScheduler) swtich2SelfDeliverWithRetry(savedOrderInfo *WatchOrderInf } } else { s.removeWaybillFromMap(savedOrderInfo, order.VendorID) - partner.CurOrderManager.UpdateOrderStatusAndFlag(order) } } else { // 进到这里的原因是,在这个时间点,购物平台物流已经抢单(但抢单消息还没有被收到),所以转自送会失败 (比如:818810379000941),更好的做法应该是判断Swtich2SelfDeliver的返回值,这种情况下就不得试了 @@ -603,20 +603,17 @@ func (s *DefScheduler) swtich2SelfDeliverWithRetry(savedOrderInfo *WatchOrderInf } // 这个函数这样写的原因是适应一些消息错序 -func (s *DefScheduler) loadSavedOrderFromMap(status *model.OrderStatus, isAutoLoad bool) *WatchOrderInfo { +func (s *DefScheduler) loadSavedOrderFromMap(status *model.OrderStatus, isForceLoad bool) *WatchOrderInfo { globals.SugarLogger.Debugf("loadSavedOrderFromMap status:%v", status) universalOrderID := jxutils.ComposeUniversalOrderID(status.RefVendorOrderID, status.RefVendorID) var realSavedInfo *WatchOrderInfo if savedInfo, ok := s.orderMap.Load(universalOrderID); ok { realSavedInfo = savedInfo.(*WatchOrderInfo) + } else { + realSavedInfo = NewWatchOrderInfo(nil) + s.orderMap.StoreWithTimeout(universalOrderID, realSavedInfo, orderMapStoreMaxTime) } - if isAutoLoad && (realSavedInfo == nil || !model.IsOrderSolid(realSavedInfo.order)) { - if realSavedInfo == nil { - realSavedInfo = NewWatchOrderInfo(nil) - s.orderMap.StoreWithTimeout(universalOrderID, realSavedInfo, orderMapStoreMaxTime) - } else { - globals.SugarLogger.Infof("loadSavedOrderFromMap order is incomplete, orderID:%s, load it", status.RefVendorOrderID) - } + if isForceLoad { if order, err := partner.CurOrderManager.LoadOrder(status.RefVendorOrderID, status.RefVendorID); err == nil { realSavedInfo.SetOrder(order) } else { @@ -684,6 +681,7 @@ func (s *DefScheduler) resetTimer(savedOrderInfo *WatchOrderInfo, bill *model.Wa savedOrderInfo.timer = utils.AfterFuncWithRecover(timeout, func() { jxutils.CallMsgHandlerAsync(func() { globals.SugarLogger.Debugf("fire timer:%s, orderID:%s", timerName, order.VendorOrderID) + savedOrderInfo := s.loadSavedOrderFromMap(model.Order2Status(order), true) config.TimeoutAction(savedOrderInfo) savedOrderInfo.timerStatus = 0 savedOrderInfo.timerStatusType = scheduler.TimerStatusTypeUnknown @@ -808,13 +806,13 @@ func (s *DefScheduler) handleAutoAcceptOrder(orderID string, vendorID int, userM return handleType } -func (s *DefScheduler) updateOrderByStatus(order *model.GoodsOrder, status *model.OrderStatus) (retVal *model.GoodsOrder) { - order.Status = status.Status - order.VendorStatus = status.VendorStatus - order.StatusTime = status.StatusTime - order.LockStatus = status.LockStatus - return order -} +// func (s *DefScheduler) updateOrderByStatus(order *model.GoodsOrder, status *model.OrderStatus) (retVal *model.GoodsOrder) { +// order.Status = status.Status +// order.VendorStatus = status.VendorStatus +// order.StatusTime = status.StatusTime +// order.LockStatus = status.LockStatus +// return order +// } func (s *DefScheduler) updateOrderByBill(order *model.GoodsOrder, bill *model.Waybill, revertStatus bool) { if order.Status > model.OrderStatusEndBegin { @@ -828,6 +826,7 @@ func (s *DefScheduler) updateOrderByBill(order *model.GoodsOrder, bill *model.Wa order.VendorWaybillID = bill.VendorWaybillID if revertStatus { order.Status = model.OrderStatusFinishedPickup + partner.CurOrderManager.UpdateOrderStatusAndFlag(order) } } diff --git a/business/model/order.go b/business/model/order.go index 2b4832a2f..87ea6f1ac 100644 --- a/business/model/order.go +++ b/business/model/order.go @@ -157,7 +157,7 @@ type OrderStatus struct { DuplicatedCount int `json:"-"` // 收到的重复状态转换(或消息)数,一般是由于重发造成的 Remark string `orm:"size(255)" json:"remark"` ModelTimeInfo `json:"-"` - LockStatus int `orm:"-" json:"-"` // todo 只是用于传递状态,应该可以优化掉 + // LockStatus int `orm:"-" json:"-"` // todo 只是用于传递状态,应该可以优化掉 } func (v *OrderStatus) TableIndex() [][]string { @@ -177,7 +177,7 @@ func Order2Status(order *GoodsOrder) (retVal *OrderStatus) { Status: order.Status, VendorStatus: order.VendorStatus, StatusTime: order.StatusTime, - LockStatus: order.LockStatus, + // LockStatus: order.LockStatus, } return retVal } @@ -199,7 +199,7 @@ func Waybill2Status(bill *Waybill) (retVal *OrderStatus) { // 判断订单是否是临时的,不是真实收到了new order消息后的订单 func IsOrderSolid(order *GoodsOrder) bool { - return !(order.ConsigneeName == "" && order.ID == 0) + return order != nil && !(order.ConsigneeName == "" && order.ID == 0) } func (o *GoodsOrder) GetStatusTime() time.Time {