From 6b3b0bcd3522c692ae16232d1506147de698d411 Mon Sep 17 00:00:00 2001 From: Rosy-zhudan Date: Thu, 12 Sep 2019 15:36:39 +0800 Subject: [PATCH] =?UTF-8?q?=E9=97=A8=E5=BA=97=E8=AF=84=E5=88=86-=E4=BC=98?= =?UTF-8?q?=E5=8C=96=E6=95=B0=E6=8D=AE=E8=AF=BB=E5=8F=96=E9=80=9F=E5=BA=A6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- business/jxstore/misc/store_score.go | 193 ++++++++++++++++----------- business/model/dao/dao_order.go | 38 +++--- business/model/store_score.go | 5 + 3 files changed, 139 insertions(+), 97 deletions(-) diff --git a/business/jxstore/misc/store_score.go b/business/jxstore/misc/store_score.go index 65882fac9..0ab3a6056 100644 --- a/business/jxstore/misc/store_score.go +++ b/business/jxstore/misc/store_score.go @@ -19,7 +19,7 @@ import ( const ( EnableScheduleScoreStore = !true - ParallelCount = 10 + ParallelCount = 5 GoldMedalScore = 90 SilverMedalScore = 80 @@ -71,13 +71,11 @@ var ( ) type AllStoreSkusWrapper struct { - //allStoreSkus map[int]map[int]*cms.StoreSkuNameExt allStoreSkus map[int]map[int]int locker sync.RWMutex } func (a *AllStoreSkusWrapper) InitData() { - // a.allStoreSkus = make(map[int]map[int]*cms.StoreSkuNameExt) a.allStoreSkus = make(map[int]map[int]int) } @@ -85,17 +83,6 @@ func (a *AllStoreSkusWrapper) ClearData() { a.allStoreSkus = nil } -// func (a *AllStoreSkusWrapper) SetData(storeID int, skuMapData map[int]*cms.StoreSkuNameExt) { -// a.locker.Lock() -// defer a.locker.Unlock() -// a.allStoreSkus[storeID] = skuMapData -// } - -// func (a *AllStoreSkusWrapper) GetData(storeID int) map[int]*cms.StoreSkuNameExt { -// a.locker.RLock() -// defer a.locker.RUnlock() -// return a.allStoreSkus[storeID] -// } func (a *AllStoreSkusWrapper) SetData(storeID int, skuMapData map[int]int) { a.locker.Lock() defer a.locker.Unlock() @@ -109,12 +96,28 @@ func (a *AllStoreSkusWrapper) GetData(storeID int) map[int]int { } type StoreScoreDataWrapper struct { - storeScoreData map[int]*model.StoreScore - locker sync.RWMutex + storeScoreData map[int]*model.StoreScore + dailyBadCommentOrderCount map[int]int + dailyUnFinishOrderCount map[int]int + dailyFinishOrderCount map[int]int + dailyAbsentGoodsOrderCount map[int]int + locker sync.RWMutex } func (s *StoreScoreDataWrapper) InitData() { s.storeScoreData = make(map[int]*model.StoreScore) + s.dailyBadCommentOrderCount = make(map[int]int) + s.dailyUnFinishOrderCount = make(map[int]int) + s.dailyFinishOrderCount = make(map[int]int) + s.dailyAbsentGoodsOrderCount = make(map[int]int) +} + +func (s *StoreScoreDataWrapper) ClearData() { + s.storeScoreData = nil + s.dailyBadCommentOrderCount = nil + s.dailyUnFinishOrderCount = nil + s.dailyFinishOrderCount = nil + s.dailyAbsentGoodsOrderCount = nil } func (s *StoreScoreDataWrapper) SetData(storeID int, valueName string, value int) { @@ -130,6 +133,78 @@ func (s *StoreScoreDataWrapper) SetData(storeID int, valueName string, value int valueInfo.FieldByName(valueName).SetInt(int64(value)) } +func (s *StoreScoreDataWrapper) SetDailyBadCommentOrderCount(storeCountList []*model.StoreCount) { + s.locker.Lock() + defer s.locker.Unlock() + for _, value := range storeCountList { + s.dailyBadCommentOrderCount[value.StoreID] = value.Count + } +} + +func (s *StoreScoreDataWrapper) GetDailyBadCommentOrderCount(storeID int) int { + s.locker.RLock() + defer s.locker.RUnlock() + if count, ok := s.dailyBadCommentOrderCount[storeID]; ok { + return count + } + + return 0 +} + +func (s *StoreScoreDataWrapper) SetDailyUnFinishOrderCount(storeCountList []*model.StoreCount) { + for _, value := range storeCountList { + s.dailyUnFinishOrderCount[value.StoreID] = value.Count + } +} + +func (s *StoreScoreDataWrapper) GetDailyUnFinishOrderCount(storeID int) int { + s.locker.RLock() + defer s.locker.RUnlock() + if count, ok := s.dailyUnFinishOrderCount[storeID]; ok { + return count + } + + return 0 +} + +func (s *StoreScoreDataWrapper) SetDailyFinishOrderCount(storeCountList []*model.StoreCount) { + for _, value := range storeCountList { + s.dailyFinishOrderCount[value.StoreID] = value.Count + } +} + +func (s *StoreScoreDataWrapper) GetDailyFinishOrderCount(storeID int) int { + s.locker.RLock() + defer s.locker.RUnlock() + if count, ok := s.dailyFinishOrderCount[storeID]; ok { + return count + } + + return 0 +} + +func (s *StoreScoreDataWrapper) SetDailyAbsentGoodsOrderCount(storeCountList []*model.StoreCount) { + for _, value := range storeCountList { + s.dailyAbsentGoodsOrderCount[value.StoreID] = value.Count + } +} + +func (s *StoreScoreDataWrapper) GetDailyAbsentGoodsOrderCount(storeID int) int { + s.locker.RLock() + defer s.locker.RUnlock() + if count, ok := s.dailyAbsentGoodsOrderCount[storeID]; ok { + return count + } + + return 0 +} + +func (s *StoreScoreDataWrapper) InsertStoreScore() { + for _, value := range s.storeScoreData { + dao.InsertStoreScore(value) + } +} + //得到所有门店的可售商品(优化内存,只存商品的价格) func GetAllStoreSkus(ctx *jxcontext.Context, parentTask tasksch.ITask, storeList []*cms.StoreExt) { allStoreSkusWrapper.InitData() @@ -137,13 +212,11 @@ func GetAllStoreSkus(ctx *jxcontext.Context, parentTask tasksch.ITask, storeList storeInfo := batchItemList[0].(*cms.StoreExt) storeID := storeInfo.ID jxSkuInfoData, _ := cms.GetStoreSkus(ctx, storeID, []int{}, true, "", true, map[string]interface{}{}, 0, -1) - //jxSkuMapData := make(map[int]*cms.StoreSkuNameExt) jxSkuPriceMapData := make(map[int]int) for _, value := range jxSkuInfoData.SkuNames { for _, skuInfo := range value.Skus2 { saleStatus := jxutils.MergeSkuStatus(skuInfo.SkuStatus, skuInfo.StoreSkuStatus) if saleStatus == model.SkuStatusNormal { - //jxSkuMapData[skuInfo.SkuID] = value jxSkuPriceMapData[skuInfo.SkuID] = skuInfo.BindPrice } } @@ -151,7 +224,7 @@ func GetAllStoreSkus(ctx *jxcontext.Context, parentTask tasksch.ITask, storeList allStoreSkusWrapper.SetData(storeID, jxSkuPriceMapData) return retVal, err } - taskParallel := tasksch.NewParallelTask("得到所有门店商品", nil, ctx, taskFunc, storeList) + taskParallel := tasksch.NewParallelTask("得到所有门店商品", tasksch.NewParallelConfig().SetParallelCount(ParallelCount), ctx, taskFunc, storeList) tasksch.HandleTask(taskParallel, parentTask, true).Run() taskParallel.GetResult(0) } @@ -251,15 +324,10 @@ func ScoreAveragePickupTime(storeInfo *cms.StoreExt) { } //差评订单和完成订单比例小于0.2%,得满分10分,每增加0.1%减1分 -func ScoreBadCommentOrder(storeInfo *cms.StoreExt, paramFinishOrderCount int64) (finishOrderCount int64) { +func ScoreBadCommentOrder(storeInfo *cms.StoreExt) { storeID := storeInfo.ID - db := dao.GetDB() - badCommentOrderCount, _ := dao.GetDailyBadCommentOrderCount(db, storeID) - if paramFinishOrderCount == -1 { - finishOrderCount, _ = dao.GetDailyFinishOrderCount(db, storeID) - } else { - finishOrderCount = paramFinishOrderCount - } + badCommentOrderCount := storeScoreDataWrapper.GetDailyBadCommentOrderCount(storeID) + finishOrderCount := storeScoreDataWrapper.GetDailyFinishOrderCount(storeID) finalScore := 0 if finishOrderCount > 0 { badCommentOrderRatio := float64(badCommentOrderCount) * 100 / float64(finishOrderCount) @@ -274,20 +342,13 @@ func ScoreBadCommentOrder(storeInfo *cms.StoreExt, paramFinishOrderCount int64) } } storeScoreDataWrapper.SetData(storeID, model.FieldBadCommentOrder, finalScore) - - return finishOrderCount } //未完成订单和完成订单比小于1%,得满分10分,比例每增加5%,分数减1 -func ScoreUnfinishOrder(storeInfo *cms.StoreExt, paramFinishOrderCount int64) (finishOrderCount int64) { +func ScoreUnfinishOrder(storeInfo *cms.StoreExt) { storeID := storeInfo.ID - db := dao.GetDB() - unFinishOrderCount, _ := dao.GetDailyUnFinishOrderCount(db, storeID) - if paramFinishOrderCount == -1 { - finishOrderCount, _ = dao.GetDailyFinishOrderCount(db, storeID) - } else { - finishOrderCount = paramFinishOrderCount - } + unFinishOrderCount := storeScoreDataWrapper.GetDailyUnFinishOrderCount(storeID) + finishOrderCount := storeScoreDataWrapper.GetDailyFinishOrderCount(storeID) finalScore := 0 if finishOrderCount > 0 { unfinishOrderRatio := float64(unFinishOrderCount) * 100 / float64(finishOrderCount) @@ -302,20 +363,13 @@ func ScoreUnfinishOrder(storeInfo *cms.StoreExt, paramFinishOrderCount int64) (f } } storeScoreDataWrapper.SetData(storeID, model.FieldUnfinishOrder, finalScore) - - return finishOrderCount } //缺货订单和完成订单比小于1%得10分,比例每增加0.1%减1分 -func ScoreAbsentGoodsOrder(storeInfo *cms.StoreExt, paramFinishOrderCount int64) (finishOrderCount int64) { +func ScoreAbsentGoodsOrder(storeInfo *cms.StoreExt) { storeID := storeInfo.ID - db := dao.GetDB() - absentGoodsOrderCount, _ := dao.GetDailyAbsentGoodsOrderCount(db, storeID) - if paramFinishOrderCount == -1 { - finishOrderCount, _ = dao.GetDailyFinishOrderCount(db, storeID) - } else { - finishOrderCount = paramFinishOrderCount - } + absentGoodsOrderCount := storeScoreDataWrapper.GetDailyAbsentGoodsOrderCount(storeID) + finishOrderCount := storeScoreDataWrapper.GetDailyFinishOrderCount(storeID) finalScore := 0 if finishOrderCount > 0 { absentGoodsOrderRatio := float64(absentGoodsOrderCount) * 100 / float64(finishOrderCount) @@ -330,8 +384,6 @@ func ScoreAbsentGoodsOrder(storeInfo *cms.StoreExt, paramFinishOrderCount int64) } } storeScoreDataWrapper.SetData(storeID, model.FieldAbsentGoodsOrder, finalScore) - - return finishOrderCount } //促销品数量20个以上为满分10分,每少2个扣1分 @@ -447,12 +499,6 @@ func GetStoreSkusAveragePrice(storeList []*cms.StoreExt) map[int]int { for _, storeInfo := range storeList { storeID := storeInfo.ID storeSkuMapData := allStoreSkusWrapper.GetData(storeID) - // for _, value := range storeSkuMapData { - // skuID := value.Skus2[0].SkuID - // skuPrice := value.Skus2[0].BindPrice - // skusTotalPrice[skuID] += skuPrice - // skusCount[skuID]++ - // } for skuID, skuPrice := range storeSkuMapData { skusTotalPrice[skuID] += skuPrice skusCount[skuID]++ @@ -466,14 +512,6 @@ func GetStoreSkusAveragePrice(storeList []*cms.StoreExt) map[int]int { func GetSkusCountLessEqualAvgPrice(storeID int, skusAveragePrice map[int]int) (count int) { storeSkuMapData := allStoreSkusWrapper.GetData(storeID) - // for _, value := range storeSkuMapData { - // skuID := value.Skus2[0].SkuID - // skuPrice := value.Skus2[0].BindPrice - // skuAvgPrice := skusAveragePrice[skuID] - // if skuPrice <= skuAvgPrice { - // count++ - // } - // } for skuID, skuPrice := range storeSkuMapData { skuAvgPrice := skusAveragePrice[skuID] if skuPrice <= skuAvgPrice { @@ -536,7 +574,7 @@ func GetFilterStoreListEx(storeList []*cms.StoreExt, storeIDMap map[int]int) (ou func ScoreStore(ctx *jxcontext.Context, storeIDList []int) (retVal interface{}, err error) { var storeList []*cms.StoreExt - taskCount := 4 + taskCount := 5 taskSeqFunc := func(task *tasksch.SeqTask, step int, params ...interface{}) (result interface{}, err error) { switch step { case 0: @@ -551,6 +589,16 @@ func ScoreStore(ctx *jxcontext.Context, storeIDList []int) (retVal interface{}, GetAllStoreSkus(ctx, task, storeList) baseapi.SugarLogger.Debugf("ScoreStore step1 end") case 2: + db := dao.GetDB() + storeCountList, _ := dao.GetDailyBadCommentOrderCount(db) + storeScoreDataWrapper.SetDailyBadCommentOrderCount(storeCountList) + storeCountList, _ = dao.GetDailyUnFinishOrderCount(db) + storeScoreDataWrapper.SetDailyUnFinishOrderCount(storeCountList) + storeCountList, _ = dao.GetDailyFinishOrderCount(db) + storeScoreDataWrapper.SetDailyFinishOrderCount(storeCountList) + storeCountList, _ = dao.GetDailyAbsentGoodsOrderCount(db) + storeScoreDataWrapper.SetDailyAbsentGoodsOrderCount(storeCountList) + case 3: baseapi.SugarLogger.Debugf("ScoreStore step2 begin") taskFunc := func(task *tasksch.ParallelTask, batchItemList []interface{}, params ...interface{}) (retVal interface{}, err error) { storeInfo := batchItemList[0].(*cms.StoreExt) @@ -559,9 +607,9 @@ func ScoreStore(ctx *jxcontext.Context, storeIDList []int) (retVal interface{}, ScoreStoreOpenTime(storeInfo) ScoreSaleSkuCount(storeInfo) ScoreAveragePickupTime(storeInfo) - finishOrderCount := ScoreBadCommentOrder(storeInfo, -1) - ScoreUnfinishOrder(storeInfo, finishOrderCount) - ScoreAbsentGoodsOrder(storeInfo, finishOrderCount) + ScoreBadCommentOrder(storeInfo) + ScoreUnfinishOrder(storeInfo) + ScoreAbsentGoodsOrder(storeInfo) ScorePromotionSku(storeInfo) ScoreFullVendor(storeInfo) ScoreStoreRange(storeInfo) @@ -577,9 +625,10 @@ func ScoreStore(ctx *jxcontext.Context, storeIDList []int) (retVal interface{}, baseapi.SugarLogger.Debugf("ScoreStore taskParallel error:%v", err) } baseapi.SugarLogger.Debugf("ScoreStore step2 end") - case 3: + case 4: baseapi.SugarLogger.Debugf("ScoreStore step3 begin") - InsertStoreScore() + storeScoreDataWrapper.InsertStoreScore() + storeScoreDataWrapper.ClearData() allStoreSkusWrapper.ClearData() baseapi.SugarLogger.Debugf("ScoreStore step3 end") } @@ -591,12 +640,6 @@ func ScoreStore(ctx *jxcontext.Context, storeIDList []int) (retVal interface{}, return retVal, err } -func InsertStoreScore() { - for _, value := range storeScoreDataWrapper.storeScoreData { - dao.InsertStoreScore(value) - } -} - func ScheduleScoreStore() { if EnableScheduleScoreStore { ScheduleTimerFunc("ScheduleScoreStore", func() { diff --git a/business/model/dao/dao_order.go b/business/model/dao/dao_order.go index e103524e1..4a979dfb5 100644 --- a/business/model/dao/dao_order.go +++ b/business/model/dao/dao_order.go @@ -306,42 +306,36 @@ func GetDailyFinishOrderList(db *DaoDB, storeID int) (orderList []*model.OrderPi return orderList, GetRows(db, &orderList, sql, sqlParams...) } -func GetDailyBadCommentOrderCount(db *DaoDB, storeID int) (count int64, err error) { - sql := `select count(*) from jx_bad_comments where DATE(createtime) = CURDATE() and jxstoreid = ?` - sqlParams := []interface{}{ - storeID, - } - err = GetRow(db, &count, sql, sqlParams...) +func GetDailyBadCommentOrderCount(db *DaoDB) (storeCountList []*model.StoreCount, err error) { + sql := `select jxstoreid store_id, COUNT(*) count from jx_bad_comments where DATE(createtime) = CURDATE() GROUP BY jxstoreid` + err = GetRows(db, &storeCountList, sql) - return count, err + return storeCountList, err } -func GetDailyUnFinishOrderCount(db *DaoDB, storeID int) (num int64, err error) { - return GetDailyEndOrderCount(db, storeID, []int{model.OrderStatusCanceled}, false) +func GetDailyUnFinishOrderCount(db *DaoDB) (storeCountList []*model.StoreCount, err error) { + return GetDailyEndOrderCount(db, []int{model.OrderStatusCanceled}, false) } -func GetDailyFinishOrderCount(db *DaoDB, storeID int) (num int64, err error) { - return GetDailyEndOrderCount(db, storeID, []int{model.OrderStatusFinished}, false) +func GetDailyFinishOrderCount(db *DaoDB) (storeCountList []*model.StoreCount, err error) { + return GetDailyEndOrderCount(db, []int{model.OrderStatusFinished}, false) } -func GetDailyAbsentGoodsOrderCount(db *DaoDB, storeID int) (num int64, err error) { - return GetDailyEndOrderCount(db, storeID, []int{model.OrderStatusFinished, model.OrderStatusCanceled}, true) +func GetDailyAbsentGoodsOrderCount(db *DaoDB) (storeCountList []*model.StoreCount, err error) { + return GetDailyEndOrderCount(db, []int{model.OrderStatusFinished, model.OrderStatusCanceled}, true) } -func GetDailyEndOrderCount(db *DaoDB, storeID int, statusList []int, isAbsentOrder bool) (count int64, err error) { - sql := `SELECT COUNT(*) FROM goods_order +func GetDailyEndOrderCount(db *DaoDB, statusList []int, isAbsentOrder bool) (storeCountList []*model.StoreCount, err error) { + sql := `SELECT jx_store_id store_id, COUNT(*) count FROM goods_order WHERE DATE(order_finished_at) = CURDATE() - AND jx_store_id = ? AND status IN (` + GenQuestionMarks(len(statusList)) + `)` if isAbsentOrder { sql += ` AND adjust_count > 0` } - sqlParams := []interface{}{ - storeID, - } - sqlParams = append(sqlParams, statusList) - err = GetRow(db, &count, sql, sqlParams...) + sql += ` + GROUP BY jx_store_id` + err = GetRow(db, &storeCountList, sql) - return count, err + return storeCountList, err } diff --git a/business/model/store_score.go b/business/model/store_score.go index c8207a7cd..5529b4269 100644 --- a/business/model/store_score.go +++ b/business/model/store_score.go @@ -47,3 +47,8 @@ type WeeklyStoreScore struct { ItemTotalScore int `json:"itemTotalScore"` Level int `json:"level"` } + +type StoreCount struct { + StoreID int `orm:"column(store_id)"` + Count int +}