- 梳理TIMER,去除TimerTypeBaseExpectedDeliveredTime

This commit is contained in:
gazebo
2019-03-31 15:46:41 +08:00
parent d2fafe5ec0
commit ef05d85fc2
9 changed files with 132 additions and 119 deletions

View File

@@ -23,11 +23,13 @@ import (
)
const (
time2Delivered = 1 * time.Hour // 正常从下单到送达的时间。
time2Schedule3rdCarrier = 20 // 收到平台方自有配送的新运单消息后等待创建三方配送运单的时间分钟如果是定时达会再根据ExpectedDeliveredTime与dingShiDaAheadTime做调整
// time2Schedule3rdCarrierGap4OrderStatus = 3 * time.Minute // 京东要求是运单状态为待抢单且超时5分钟但为了防止没有运单事件所以就拣货完成事件开始算添加3分钟
time2AutoPickupMin = 15 * time.Minute // 自动拣货等待时间这个只有在没有PickDeadline信息才有用否则会根据PickDeadline设置
time2AutoPickupGap = 1 * 60 //随机1分钟
time2Delivered = 1 * time.Hour // 正常从下单到送达的时间。
minute2Schedule3rdCarrier = 20 // 收到平台方自有配送的新运单消息后等待创建三方配送运单的时间分钟如果是定时达会再根据ExpectedDeliveredTime与dingShiDaAheadTime做调整
minMinute2Schedule3rdCarrier = 5 // 转三方配送最少等待时间(分钟
time2AutoPickupMin = 15 * time.Minute // 自动拣货等待时间这个只有在没有PickDeadline信息才有用否则会根据PickDeadline设置
second2AutoPickupGap = 60 //随机60秒
time2AutoPickupAhead = 20 * time.Second // 有最后拣货时间的提前值
// 把pending order timerout 在-pendingOrderTimerMinMinSecond至pendingOrderTimerMaxSecond映射到pendingOrderTimerMinSecond至pendingOrderTimerMaxSecond
pendingOrderTimerMinMinSecond = 5 * 60 // 5分钟
@@ -155,9 +157,9 @@ func init() {
},
model.OrderStatusAccepted: &StatusActionConfig{ // 自动拣货
StatusActionParams: partner.StatusActionParams{
TimerType: partner.TimerTypeBaseExpectedDeliveredTime,
Timeout: time2AutoPickupMin, // 此值会被门店设置覆盖
TimeoutGap: time2AutoPickupGap,
TimerType: partner.TimerTypeBaseStatusTime,
Timeout: time2AutoPickupMin,
TimeoutGap: second2AutoPickupGap,
},
TimeoutAction: func(savedOrderInfo *WatchOrderInfo) (err error) {
if savedOrderInfo.autoPickupTimeoutMinute > 0 {
@@ -184,10 +186,10 @@ func init() {
model.WaybillStatusNew: &StatusActionConfig{
StatusActionParams: partner.StatusActionParams{
TimerType: partner.TimerTypeBaseStatusTime,
Timeout: time2Schedule3rdCarrier * time.Minute,
Timeout: minute2Schedule3rdCarrier * time.Minute,
},
TimeoutAction: func(savedOrderInfo *WatchOrderInfo) (err error) {
if savedOrderInfo.storeDeliveryType != scheduler.StoreDeliveryTypeByStore { // 非自配商家使用
if savedOrderInfo.storeDeliveryType != scheduler.StoreDeliveryTypeByStore { // 非自配商家使用
return sch.createWaybillOn3rdProviders(savedOrderInfo, nil)
}
return nil
@@ -199,7 +201,7 @@ func init() {
func Init() {
configindb.WatchConfigChange(time2Schedule3rdCarrierKey, OnDefSchConfChanged)
if configTime, err := configindb.GetConfig(time2Schedule3rdCarrierKey, utils.Int2Str(time2Schedule3rdCarrier)); err == nil {
if configTime, err := configindb.GetConfig(time2Schedule3rdCarrierKey, utils.Int2Str(minute2Schedule3rdCarrier)); err == nil {
OnDefSchConfChanged(time2Schedule3rdCarrierKey, configTime)
} else {
globals.SugarLogger.Errorf("defsch Init, error:%v", err)
@@ -629,38 +631,12 @@ func (s *DefScheduler) resetTimer(savedOrderInfo *WatchOrderInfo, bill *model.Wa
}
globals.SugarLogger.Debugf("resetTimer, orderID:%s statusType:%d status:%v", order.VendorOrderID, statusType, status)
if statusType != savedOrderInfo.timerStatusType || status >= savedOrderInfo.timerStatus { // 新设置的TIMER不能覆盖状态在其后的TIMER如果状态回绕需要注意
config := s.mergeOrderStatusConfig(savedOrderInfo.order, statusType, status, order.VendorID)
config := s.mergeOrderStatusConfig(savedOrderInfo, statusTime, statusType, status)
if config == nil || config.TimerType != partner.TimerTypeByPass {
s.stopTimer(savedOrderInfo)
}
if config != nil && config.TimeoutAction != nil && config.TimerType != partner.TimerTypeByPass {
nowTime := time.Now()
configTimerType := config.TimerType
if statusType == scheduler.TimerStatusTypeOrder && status == model.OrderStatusAccepted { // 自动拣货的TIMER特殊处理
if !utils.IsTimeZero(order.PickDeadline) { // 如果有PickDeadline值特殊处理
configTimerType = partner.TimerTypeBaseNow
config.Timeout = order.PickDeadline.Sub(nowTime) - 20*time.Second // 提前一点操作,防止超时
if config.TimeoutGap != 0 {
config.Timeout -= time.Duration(config.TimeoutGap) * time.Second
}
} else if savedOrderInfo.autoPickupTimeoutMinute > 1 { // 对于自动拣货,以订单中的设置为准
config.Timeout = time.Duration(savedOrderInfo.autoPickupTimeoutMinute) * time.Minute
}
}
var timeout time.Duration
switch configTimerType {
case partner.TimerTypeBaseNow:
timeout = config.Timeout
case partner.TimerTypeBaseStatusTime:
timeout = statusTime.Sub(nowTime) + config.Timeout
case partner.TimerTypeBaseExpectedDeliveredTime:
if order.BusinessType == model.BusinessTypeDingshida && !utils.IsTimeZero(order.ExpectedDeliveredTime) {
statusTime = order.ExpectedDeliveredTime.Add(-time2Delivered)
}
timeout = statusTime.Sub(nowTime) + config.Timeout
default:
panic("TimerType is wrong!!!")
}
timeout := config.GetRefTimeout(statusTime)
if config.TimeoutGap != 0 {
timeout += time.Duration(rand.Intn(int(config.TimeoutGap))) * time.Second
}
@@ -694,6 +670,87 @@ func (s *DefScheduler) resetTimer(savedOrderInfo *WatchOrderInfo, bill *model.Wa
}
}
func (s *DefScheduler) mergeOrderStatusConfig(savedOrderInfo *WatchOrderInfo, statusTime time.Time, statusType, status int) (retVal *StatusActionConfig) {
s.locker.RLock()
defer func() {
s.locker.RUnlock()
}()
defConfig := s.defWorkflowConfig[statusType][status]
if defConfig == nil {
return nil
}
retVal = &StatusActionConfig{}
*retVal = *defConfig
order := savedOrderInfo.order
var vendorActionParams *partner.StatusActionParams
// 非立即达订单timer设置
if model.IsOrderSolid(order) {
if order.BusinessType != model.BusinessTypeImmediate { // 非立即达订单
if utils.IsTimeZero(order.ExpectedDeliveredTime) {
globals.SugarLogger.Warnf("mergeOrderStatusConfig orderID:%s 非立即达订单没有预计送达时间, orderDetail:%s", order.VendorOrderID, utils.Format4Output(order, false))
} else if statusType == scheduler.TimerStatusTypeOrder && status == model.OrderStatusFinishedPickup { // 这个只针对自配送门店才有效
vendorActionParams = &partner.StatusActionParams{
TimerType: partner.TimerTypeBaseNow,
Timeout: order.ExpectedDeliveredTime.Sub(time.Now()) - dingShiDaAheadTime,
TimeoutGap: -1,
}
timeout := statusTime.Sub(time.Now()) + minMinute2Schedule3rdCarrier*time.Minute
if vendorActionParams.GetRefTimeout(statusTime) < timeout { // 如果非立即达订单根据ExpectedDeliveredTime算出来的timeout太早
vendorActionParams.Timeout = timeout
vendorActionParams.TimeoutGap = 0
}
} else if statusType == scheduler.TimerStatusTypeWaybill && status == model.WaybillStatusNew { // 因为有些平台(比如美团外卖)的定时达单,很早就创建运单了
vendorActionParams = &partner.StatusActionParams{
TimerType: partner.TimerTypeBaseNow,
Timeout: order.ExpectedDeliveredTime.Sub(time.Now()) - dingShiDaAheadTime,
TimeoutGap: -1,
}
}
}
}
if vendorActionParams == nil {
vendorActionParams = partner.GetPurchasePlatformFromVendorID(order.VendorID).GetStatusActionTimeout(order, statusType, status)
}
// 自动拣货TIMER
if statusType == scheduler.TimerStatusTypeOrder && status == model.OrderStatusAccepted {
if savedOrderInfo.autoPickupTimeoutMinute > 0 {
if utils.IsTimeZero(order.PickDeadline) { // 没有最后拣货时间,正推,以订单中的配置为准
if utils.IsTimeZero(order.ExpectedDeliveredTime) || order.BusinessType == model.BusinessTypeImmediate { // 立即达或没有最后送达时间
// 以缺省配置或平台相关中的配置为准
} else { // 非立即达且有最后送达时间
timeout := time2AutoPickupMin
if savedOrderInfo.autoPickupTimeoutMinute > 1 {
timeout = time.Duration(savedOrderInfo.autoPickupTimeoutMinute) * time.Minute
}
vendorActionParams = &partner.StatusActionParams{
TimerType: partner.TimerTypeBaseNow,
Timeout: order.ExpectedDeliveredTime.Add(-time2Delivered).Sub(time.Now()) + timeout,
}
}
} else { // 有最后拣货时间,反推
vendorActionParams = &partner.StatusActionParams{
TimerType: partner.TimerTypeBaseNow,
Timeout: order.PickDeadline.Sub(time.Now()) - time2AutoPickupAhead - second2AutoPickupGap*time.Second,
TimeoutGap: second2AutoPickupGap,
}
}
}
}
if vendorActionParams != nil {
retVal.Timeout = vendorActionParams.Timeout
if vendorActionParams.TimeoutGap >= 0 {
retVal.TimeoutGap = vendorActionParams.TimeoutGap
}
if vendorActionParams.TimerType != partner.TimerTypeNoOverride {
retVal.TimerType = vendorActionParams.TimerType
}
}
return retVal
}
func (s *DefScheduler) handleAutoAcceptOrder(orderID string, vendorID int, userMobile string, jxStoreID int, db orm.Ormer, handler func(accepted bool) error) int {
handleType := 0
if userMobile != "" {
@@ -726,53 +783,6 @@ func (s *DefScheduler) handleAutoAcceptOrder(orderID string, vendorID int, userM
return handleType
}
func (s *DefScheduler) mergeOrderStatusConfig(order *model.GoodsOrder, statusType, status int, purchaseVendorID int) (retVal *StatusActionConfig) {
s.locker.RLock()
defer func() {
s.locker.RUnlock()
}()
defConfig := s.defWorkflowConfig[statusType][status]
if defConfig == nil {
return nil
}
retVal = &StatusActionConfig{}
*retVal = *defConfig
var vendorActionParams *partner.StatusActionParams
if model.IsOrderSolid(order) {
if order.BusinessType != model.BusinessTypeImmediate {
if jxutils.IsTimeEmpty(order.ExpectedDeliveredTime) {
globals.SugarLogger.Warnf("mergeOrderStatusConfig orderID:%s 非立即达订单没有预计送达时间, orderDetail:%s", order.VendorOrderID, utils.Format4Output(order, false))
} else if statusType == scheduler.TimerStatusTypeOrder && status == model.OrderStatusFinishedPickup { // 这个只针对自配送门店才有效
vendorActionParams = &partner.StatusActionParams{
TimerType: partner.TimerTypeBaseNow,
Timeout: order.ExpectedDeliveredTime.Sub(time.Now()) - dingShiDaAheadTime,
TimeoutGap: -1,
}
} else if statusType == scheduler.TimerStatusTypeWaybill && status == model.WaybillStatusNew { // 因为有些平台(比如美团外卖)的定时达单,很早就创建运单了
vendorActionParams = &partner.StatusActionParams{
TimerType: partner.TimerTypeBaseNow,
Timeout: order.ExpectedDeliveredTime.Sub(time.Now()) - dingShiDaAheadTime,
TimeoutGap: -1,
}
}
}
}
if vendorActionParams == nil {
vendorActionParams = partner.GetPurchasePlatformFromVendorID(purchaseVendorID).GetStatusActionTimeout(order, statusType, status)
}
if vendorActionParams != nil {
retVal.Timeout = vendorActionParams.Timeout
if vendorActionParams.TimeoutGap >= 0 {
retVal.TimeoutGap = vendorActionParams.TimeoutGap
}
if vendorActionParams.TimerType != partner.TimerTypeNoOverride {
retVal.TimerType = vendorActionParams.TimerType
}
}
return retVal
}
func (s *DefScheduler) updateOrderByStatus(order *model.GoodsOrder, status *model.OrderStatus) (retVal *model.GoodsOrder) {
order.Status = status.Status
order.VendorStatus = status.VendorStatus
@@ -833,7 +843,7 @@ func (s *DefScheduler) ProxyCancelWaybill(order *model.GoodsOrder, bill *model.W
func OnDefSchConfChanged(key, value string) {
if key == time2Schedule3rdCarrierKey {
waitMinutes := int(utils.Str2Int64WithDefault(value, time2Schedule3rdCarrier))
waitMinutes := int(utils.Str2Int64WithDefault(value, minute2Schedule3rdCarrier))
if waitMinutes >= 0 {
FixedScheduler.locker.Lock()
defer func() {