From ec3265d38c77ac534508268d0e43ba3c3100cfdd Mon Sep 17 00:00:00 2001 From: "807875765@qq.com" <807875765@qq.com> Date: Mon, 18 Apr 2022 08:56:54 +0800 Subject: [PATCH] =?UTF-8?q?DIFF=20=E5=AF=B9=E6=AF=94=E5=AF=B9=E6=8E=A5?= =?UTF-8?q?=E5=81=9A=E4=BA=86=E4=BF=AE=E6=94=B9=E6=96=B0=E5=A2=9E=E4=BA=86?= =?UTF-8?q?=E7=B1=BB=E5=88=AB=E6=AF=94=E8=BE=83?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- business/jxstore/cms/store_sku.go | 439 ++++++++++++++++++++++++ business/jxstore/cms/store_sku_check.go | 120 +++++-- business/model/dao/store_sku.go | 20 +- 3 files changed, 544 insertions(+), 35 deletions(-) diff --git a/business/jxstore/cms/store_sku.go b/business/jxstore/cms/store_sku.go index 476bd1211..268434bf3 100644 --- a/business/jxstore/cms/store_sku.go +++ b/business/jxstore/cms/store_sku.go @@ -477,6 +477,10 @@ func GetStoreSkus(ctx *jxcontext.Context, storeID int, skuIDs []int, isFocus boo return GetStoresSkus(ctx, []int{storeID}, skuIDs, nil, isFocus, false, 0, keyword, isBySku, isAct, params, offset, pageSize) } +func GetStoreSkus2(ctx *jxcontext.Context, storeID int, skuIDs []int, isFocus bool, keyword string, isBySku, isAct bool, params map[string]interface{}, offset, pageSize int) (skuNamesInfo *dao.StoreSkuNamesInfo, err error) { + return GetStoresSkus2(ctx, []int{storeID}, skuIDs, nil, isFocus, false, 0, keyword, isBySku, isAct, params, offset, pageSize) +} + func getGetStoresSkusBaseSQL(db *dao.DaoDB, storeIDs, skuIDs []int, upcs []string, isFocus bool, keyword string, isBySku, isAct, isHighPrice bool, priceType int, actVendorID int, params map[string]interface{}) (sql string, sqlParams []interface{}, err error) { // 查看指定商店,对应的商品数据和商品价格等参数说明 sql = ` @@ -735,6 +739,264 @@ func getGetStoresSkusBaseSQL(db *dao.DaoDB, storeIDs, skuIDs []int, upcs []strin return sql, sqlParams, err } +func getGetStoresSkusBaseSQL2(db *dao.DaoDB, storeIDs, skuIDs []int, upcs []string, isFocus bool, keyword string, isBySku, isAct, isHighPrice bool, priceType int, actVendorID int, params map[string]interface{}) (sql string, sqlParams []interface{}, err error) { + // 查看指定商店,对应的商品数据和商品价格等参数说明 + sql = ` + FROM sku_name t1 + JOIN sku t2 FORCE INDEX(PRIMARY) ON t1.id = t2.name_id AND t2.deleted_at = ?/* AND t2.status = ?*/ + JOIN store t3 ON t3.deleted_at = ? + LEFT JOIN store_map sm ON sm.store_id = t3.id AND sm.vendor_id = ? AND sm.deleted_at = ? + LEFT JOIN store_map smm ON smm.store_id = t3.id AND smm.deleted_at = ? AND smm.vendor_id = ? + LEFT JOIN thing_map t2m ON t2m.thing_type = ? AND t2m.thing_id = t2.id AND t2m.vendor_id = sm.vendor_id AND t2m.vendor_org_code = sm.vendor_org_code AND t2m.deleted_at = ? + LEFT JOIN sku_category t8 ON t1.category_id= t8.id` + sqlParams = []interface{}{ + utils.DefaultTimeValue, + // model.SkuStatusNormal, + utils.DefaultTimeValue, + model.VendorIDJD, utils.DefaultTimeValue, // TODO 这里直接用JD有问题 + utils.DefaultTimeValue, model.VendorIDYB, + model.ThingTypeSku, utils.DefaultTimeValue, + } + if isFocus { + if isAct { // 查看活动 + sql += ` + JOIN ( + SELECT t2.store_id, t2.sku_id, + MIN(IF(t3.actual_act_price <= 0, NULL, t3.actual_act_price)) actual_act_price, /*non-zero min value*/ + MIN(IF(t2.earning_price <= 0, NULL, t2.earning_price)) earning_price /*non-zero min value*/ + FROM act t1 + JOIN act_store_sku t2 ON t2.act_id = t1.id AND t2.deleted_at = ? + JOIN act_store_sku_map t3 ON t3.bind_id = t2.id AND t3.act_id = t1.id AND (t3.sync_status & ? = 0 OR t1.type = ?) + JOIN act_map t4 ON t4.act_id = t1.id AND t4.vendor_id = t3.vendor_id AND t4.deleted_at = ? AND (t4.sync_status & ? = 0 OR t1.type = ?) + WHERE t1.deleted_at = ? AND t1.status = ? AND NOT (t1.begin_at > ? OR t1.end_at < ?)` + sqlParams = append(sqlParams, []interface{}{ + utils.DefaultTimeValue, + model.SyncFlagNewMask, + model.ActSkuFake, + utils.DefaultTimeValue, + model.SyncFlagNewMask, + model.ActSkuFake, + utils.DefaultTimeValue, + model.ActStatusCreated, + time.Now(), + time.Now(), + }) + if actVendorID >= 0 { + sql += " AND t1.vendor_mask & ? <> 0" + sqlParams = append(sqlParams, model.GetVendorMask(actVendorID)) + } + if len(storeIDs) > 0 { + sql += " AND t2.store_id IN (" + dao.GenQuestionMarks(len(storeIDs)) + ")" + sqlParams = append(sqlParams, storeIDs) + } + if len(skuIDs) > 0 { + sql += " AND t2.sku_id IN (" + dao.GenQuestionMarks(len(skuIDs)) + ")" + sqlParams = append(sqlParams, skuIDs) + } + sql += ` + GROUP BY 1, 2 + UNION + SELECT a.store_id, a.sku_id, 0 actual_act_price, 0 earning_price + FROM act_mtwm_vendor a + WHERE 1 = 1 + ` + if len(storeIDs) > 0 { + sql += " AND a.store_id IN (" + dao.GenQuestionMarks(len(storeIDs)) + ")" + sqlParams = append(sqlParams, storeIDs) + } + if len(skuIDs) > 0 { + sql += " AND a.sku_id IN (" + dao.GenQuestionMarks(len(skuIDs)) + ")" + sqlParams = append(sqlParams, skuIDs) + } + if actVendorID >= 0 && actVendorID != model.VendorIDMTWM { + sql += " AND 1 = 2" + } + sql += ` GROUP BY 1, 2, 3 + UNION + SELECT a.store_id, a.sku_id, 0 actual_act_price, 0 earning_price + FROM act_ebai_vendor_sku a + WHERE 1 = 1 + ` + if len(storeIDs) > 0 { + sql += " AND a.store_id IN (" + dao.GenQuestionMarks(len(storeIDs)) + ")" + sqlParams = append(sqlParams, storeIDs) + } + if len(skuIDs) > 0 { + sql += " AND a.sku_id IN (" + dao.GenQuestionMarks(len(skuIDs)) + ")" + sqlParams = append(sqlParams, skuIDs) + } + if actVendorID >= 0 && actVendorID != model.VendorIDEBAI { + sql += " AND 1 = 2" + } + sql += ` GROUP BY 1, 2, 3 + ) ta ON ta.store_id = t3.id AND ta.sku_id = t2.id` + } + } else { + sql += " LEFT" + } + sql += ` + JOIN store_sku_bind t4 ON t4.store_id = t3.id AND t4.sku_id = t2.id AND t4.deleted_at = ? + LEFT JOIN sku_name_place_bind t5 ON t1.id = t5.name_id AND t3.city_code = t5.place_code + LEFT JOIN price_refer_snapshot t6 ON t6.city_code = ? AND t6.sku_id = t2.id AND t6.snapshot_at = ? + LEFT JOIN store_sku_audit t7 ON t7.store_id = t3.id AND t7.name_id = t1.id AND t7.status = ? AND t7.deleted_at = ? + WHERE t1.deleted_at = ? AND (t1.is_global = 1 OR t5.id IS NOT NULL OR 1 = ?)/* AND t1.status = ?*/ + ` + sqlParams = append(sqlParams, []interface{}{ + utils.DefaultTimeValue, + 0, utils.Time2Date(time.Now().AddDate(0, 0, -1)), + model.StoreAuditStatusOnline, utils.DefaultTimeValue, + utils.DefaultTimeValue, + utils.Bool2Int(isFocus), + }) + if isHighPrice || priceType == 1 { + sql += " AND t4.unit_price > t6.mid_unit_price / IF(t3.pay_percentage < 50 , 70, t3.pay_percentage) * 1.2 * 100" + } + if priceType == -1 { + sql += " AND t4.unit_price < t6.mid_unit_price / IF(t3.pay_percentage < 50 , 70, t3.pay_percentage) / 1.2 * 100" + } + if isFocus { + sql += " AND ((t2.status = ? AND t1.status = ?) OR t4.status = ?)" + sqlParams = append(sqlParams, model.SkuStatusNormal, model.SkuStatusNormal, model.SkuStatusNormal) + } else { + sql += " AND t4.sku_id IS NULL AND (t2.status = ? AND t1.status = ?)" + sqlParams = append(sqlParams, model.SkuStatusNormal, model.SkuStatusNormal) + } + if keyword != "" { + keywordLike := "%" + keyword + "%" + sql += " AND (t1.name LIKE ? OR t1.prefix LIKE ? OR t1.upc LIKE ? OR t2.comment LIKE ?" + sqlParams = append(sqlParams, keywordLike, keywordLike, keywordLike, keywordLike) + + if keywordInt64, err2 := strconv.ParseInt(keyword, 10, 64); err2 == nil { + sql += ` + OR t1.id = ? OR t2.id = ? + OR (SELECT COUNT(*) FROM thing_map tm WHERE tm.vendor_org_code = sm.vendor_org_code AND tm.thing_type = ? AND tm.thing_id = t2.id AND tm.deleted_at = ? AND tm.vendor_thing_id = ?) > 0 + ` + sqlParams = append(sqlParams, + keywordInt64, keywordInt64, + model.ThingTypeSku, utils.DefaultTimeValue, keywordInt64) + if isFocus { + sql += " OR t4.ebai_id = ? OR t4.mtwm_id = ?" + sqlParams = append(sqlParams, keywordInt64, keywordInt64) + } + } + sql += ")" + } + + if params["nameID"] != nil { + sql += " AND t1.id = ?" + sqlParams = append(sqlParams, params["nameID"].(int)) + } + if params["nameIDs"] != nil { + var nameIDs []int + if err = utils.UnmarshalUseNumber([]byte(params["nameIDs"].(string)), &nameIDs); err != nil { + return "", nil, err + } + if len(nameIDs) > 0 { + sql += " AND t1.id IN (" + dao.GenQuestionMarks(len(nameIDs)) + ")" + sqlParams = append(sqlParams, nameIDs) + } + } + if params["categoryID"] != nil { + cat := &model.SkuCategory{} + cat.ID = params["categoryID"].(int) + if err = dao.GetEntity(db, cat); err != nil { + return "", nil, err + } + sql += " AND (t1.category_id = ?" + sqlParams = append(sqlParams, cat.ID) + if cat.Level == 1 { + sql += " OR t1.category_id IN (SELECT id FROM sku_category WHERE parent_id = ?)" + sqlParams = append(sqlParams, cat.ID) + } + sql += ")" + } + if params["name"] != nil { + sql += " AND t1.name LIKE ?" + sqlParams = append(sqlParams, "%"+params["name"].(string)+"%") + } + if params["prefix"] != nil { + sql += " AND t1.prefix LIKE ?" + sqlParams = append(sqlParams, "%"+params["prefix"].(string)+"%") + } + if params["unit"] != nil { + sql += " AND t1.unit = ?" + sqlParams = append(sqlParams, params["unit"].(string)) + } + if len(storeIDs) > 0 { + sql += " AND t3.id IN (" + dao.GenQuestionMarks(len(storeIDs)) + ")" + sqlParams = append(sqlParams, storeIDs) + if len(storeIDs) == 1 { + sql += " AND IF(INSTR(t3.name,'" + model.ExdStoreName + "') > 0, t2.exd_sku_id <> '', t2.exd_sku_id = '')" + } + } + if len(upcs) > 0 { + sql += " AND t1.upc IN (" + dao.GenQuestionMarks(len(upcs)) + ")" + sqlParams = append(sqlParams, upcs) + } + if len(skuIDs) > 0 { + sql += " AND t2.id IN (" + dao.GenQuestionMarks(len(skuIDs)) + ")" + sqlParams = append(sqlParams, skuIDs) + } else if params["skuID"] != nil { + skuID, ok := params["skuID"].(int) + if ok { + skuIDs = append(skuIDs, skuID) + sql += " AND t2.id = ?" + sqlParams = append(sqlParams, skuID) + } + } + if lockTimeStr, ok := params["lockTime"].(string); ok && lockTimeStr != "" { + if timeList, err2 := jxutils.BatchStr2Time(lockTimeStr); err2 == nil { + sql += " AND (t4.jd_lock_time > ? OR t4.mtwm_lock_time > ? OR t4.ebai_lock_time > ? OR t4.jx_lock_time > ?)" + sqlParams = append(sqlParams, timeList[0], timeList[0], timeList[0], timeList[0]) + } + } + if isFocus { + if params["fromStatus"] != nil { + fromStatus := params["fromStatus"].(int) + toStatus := fromStatus + if params["toStatus"] != nil { + toStatus = params["toStatus"].(int) + } + sql += " AND t4.status >= ? AND t4.status <= ?" + sqlParams = append(sqlParams, fromStatus, toStatus) + } + if params["jdSyncStatus"] != nil || params["ebaiSyncStatus"] != nil || params["mtwmSyncStatus"] != nil { + realVendorMap, err2 := getValidStoreVendorMap(db, storeIDs) + if err = err2; err != nil { + return "", nil, err + } + sql += " AND ( 1 = 0" + if params["jdSyncStatus"] != nil && realVendorMap[model.VendorIDJD] == 1 { + sql += " OR (t4.jd_sync_status & ? <> 0 AND t1.status = ? AND t2.status = ?)" + sqlParams = append(sqlParams, params["jdSyncStatus"], model.SkuStatusNormal, model.SkuStatusNormal) + } + if params["ebaiSyncStatus"] != nil && realVendorMap[model.VendorIDEBAI] == 1 { + sql += " OR (t4.ebai_sync_status & ? <> 0 AND NOT (t4.ebai_sync_status & ? <> 0 AND (t4.status <> ? OR t2.status <> ?)) )" + sqlParams = append(sqlParams, params["ebaiSyncStatus"], model.SyncFlagNewMask, model.SkuStatusNormal, model.SkuStatusNormal) + } + if params["mtwmSyncStatus"] != nil && realVendorMap[model.VendorIDMTWM] == 1 { + sql += " OR (t4.mtwm_sync_status & ? <> 0 AND NOT (t4.mtwm_sync_status & ? <> 0 AND (t4.status <> ? OR t2.status <> ?)) )" + sqlParams = append(sqlParams, params["mtwmSyncStatus"], model.SyncFlagNewMask, model.SkuStatusNormal, model.SkuStatusNormal) + } + sql += ")" + } + } + if isFocus { + /*前台传入的最大值和最小值设置*/ + if params["highestPrice"] != "" && params["highestPrice"] != nil { + //highestPrice := utils.Interface2Float64WithDefault(params["highestPrice"], 0) * 100 + sql += " AND t4.unit_price <= ? " + sqlParams = append(sqlParams, params["highestPrice"]) + } + if params["minimumPrice"] != "" && params["minimumPrice"] != nil { + //minimumPrice := utils.Interface2Float64WithDefault(params["minimumPrice"], 0) * 100 + sql += " AND t4.unit_price >= ? " + sqlParams = append(sqlParams, params["minimumPrice"]) + } + } + return sql, sqlParams, err +} + func GetStoresSkus(ctx *jxcontext.Context, storeIDs, skuIDs []int, upcs []string, isFocus, isHighPrice bool, priceType int, keyword string, isBySku, isAct bool, params map[string]interface{}, offset, pageSize int) (skuNamesInfo *dao.StoreSkuNamesInfo, err error) { // 管理员进入 //if /*permission.IsRoled(ctx)*/ true { @@ -762,6 +1024,10 @@ func GetStoresSkus(ctx *jxcontext.Context, storeIDs, skuIDs []int, upcs []string return GetStoresSkusNew(ctx, storeIDs, skuIDs, upcs, isFocus, isHighPrice, priceType, keyword, isBySku, isAct, params, offset, pageSize) } +func GetStoresSkus2(ctx *jxcontext.Context, storeIDs, skuIDs []int, upcs []string, isFocus, isHighPrice bool, priceType int, keyword string, isBySku, isAct bool, params map[string]interface{}, offset, pageSize int) (skuNamesInfo *dao.StoreSkuNamesInfo, err error) { + return GetStoresSkusNew2(ctx, storeIDs, skuIDs, upcs, isFocus, isHighPrice, priceType, keyword, isBySku, isAct, params, offset, pageSize) +} + func GetStoresSkusNew(ctx *jxcontext.Context, storeIDs, skuIDs []int, upcs []string, isFocus, isHighPrice bool, priceType int, keyword string, isBySku, isAct bool, params map[string]interface{}, offset, pageSize int) (skuNamesInfo *dao.StoreSkuNamesInfo, err error) { if !isFocus && !isBySku && (len(storeIDs) > 1 || len(storeIDs) == 0) { return nil, fmt.Errorf("未关注按SkuName只能查询单店") @@ -935,6 +1201,179 @@ func GetStoresSkusNew(ctx *jxcontext.Context, storeIDs, skuIDs []int, upcs []str return skuNamesInfo, err } +func GetStoresSkusNew2(ctx *jxcontext.Context, storeIDs, skuIDs []int, upcs []string, isFocus, isHighPrice bool, priceType int, keyword string, isBySku, isAct bool, params map[string]interface{}, offset, pageSize int) (skuNamesInfo *dao.StoreSkuNamesInfo, err error) { + if !isFocus && !isBySku && (len(storeIDs) > 1 || len(storeIDs) == 0) { + return nil, fmt.Errorf("未关注按SkuName只能查询单店") + } + if len(storeIDs) == 0 && len(skuIDs) == 0 && pageSize == -1 { + return nil, fmt.Errorf("GetStoresSkus必须指定storeIDs或skuIDs或分页") + } + actVendorID := -1 + if params["actVendorID"] != nil { + actVendorID = int(utils.Interface2Int64WithDefault(params["actVendorID"], -1)) + } + var highestPrice, minimumPrice float64 + if params["highestPrice"] != nil { + if highestPrice, err = strconv.ParseFloat(params["highestPrice"].(string), 64); err != nil { + delete(params, "highestPrice") + } else { + params["highestPrice"] = highestPrice * 100 + } + } + if params["minimumPrice"] != nil { + if minimumPrice, err = strconv.ParseFloat(params["minimumPrice"].(string), 64); err != nil { + delete(params, "minimumPrice") + } else { + params["minimumPrice"] = minimumPrice * 100 + } + } + if !(highestPrice > 0 && highestPrice > minimumPrice) || !(highestPrice > 0) { + delete(params, "highestPrice") + } + if !(minimumPrice >= 0 && highestPrice > 0 && highestPrice > minimumPrice) || !(minimumPrice >= 0) { + delete(params, "minimumPrice") + } + db := dao.GetDB() + sql, sqlParams, err := getGetStoresSkusBaseSQL2(db, storeIDs, skuIDs, upcs, isFocus, keyword, isBySku, isAct, isHighPrice, priceType, actVendorID, params) + if err != nil { + return nil, err + } + pageSize = jxutils.FormalizePageSize(pageSize) + offset = jxutils.FormalizePageOffset(offset) + sqlOffset := offset + sqlPageSize := pageSize + isSaleInfo := params["stFromTime"] != nil + if isSaleInfo { + sqlOffset = 0 + sqlPageSize = jxutils.FormalizePageSize(-1) + } + sqlParamsPage := []interface{}{sqlPageSize, sqlOffset} + + txDB, _ := dao.Begin(db) + defer func() { + if r := recover(); r != nil { + dao.Rollback(db, txDB) + panic(r) + } + }() + catOrderBy := "" + if params["categoryID"] != nil { + catOrderBy = "t2.seq, " + } + + skuNamesInfo = &dao.StoreSkuNamesInfo{} + if !isBySku && sqlPageSize != model.UnlimitedPageSize { + sql2 := ` + SELECT SQL_CALC_FOUND_ROWS + t3.id store_id, t1.id name_id + ` + sql + ` + GROUP BY 1, 2 + ORDER BY 1, 2 + LIMIT ? OFFSET ? + ` + sqlParams2 := append([]interface{}{}, sqlParams...) + sqlParams2 = append(sqlParams2, sqlParamsPage) + var storeNameList []*tStoreNameBind + beginTime := time.Now() + if err = dao.GetRowsTx(txDB, &storeNameList, sql2, sqlParams2...); err != nil { + dao.Rollback(db, txDB) + return nil, err + } + globals.SugarLogger.Debugf("GetStoresSkusNew get result1:%v", time.Now().Sub(beginTime)) + skuNamesInfo.TotalCount = dao.GetLastTotalRowCount2(db, txDB) + sql += " AND (1 = 0" + for _, v := range storeNameList { + sql += " OR (t1.id = ? AND t3.id = ?)" + sqlParams = append(sqlParams, v.NameID, v.StoreID) + } + sql += fmt.Sprintf(`) + ORDER BY %s t3.id, t2.name_id, t2.id`, catOrderBy) + } else { + if isFocus { + sql += fmt.Sprintf(` + ORDER BY %s t3.id, t2.name_id, t2.id`, catOrderBy) + } + sql += ` + LIMIT ? OFFSET ?` + sqlParams = append(sqlParams, sqlParamsPage) + } + sql = ` + SELECT SQL_CALC_FOUND_ROWS + t3.id store_id, t3.name store_name, t3.pay_percentage, + t1.*, + t2.name_id, t2.id sku_id, t2.spec_quality sku_spec_quality, t2.spec_unit sku_spec_unit, t2.weight, t2m.vendor_thing_id sku_jd_id, + t2.comment, t2.category_id sku_category_id, t2.status sku_status, t2.eclp_id, + t4.created_at bind_created_at, t4.updated_at bind_updated_at, t4.last_operator bind_last_operator, t4.deleted_at bind_deleted_at, + t4.sub_store_id, t4.price bind_price, IF(t4.unit_price IS NOT NULL, t4.unit_price, t1.price) unit_price, t4.status store_sku_status, t4.auto_sale_at, + t4.ebai_id, t4.mtwm_id, t4.yb_id, CONCAT(smm.yb_store_prefix,t1.yb_name_suffix) yb_sku_name, t4.jds_id, t4.jds_ware_id, + t4.jd_sync_status, t4.ebai_sync_status, t4.mtwm_sync_status, t4.yb_sync_status, t4.jds_sync_status, + t4.jd_price, t4.ebai_price, t4.mtwm_price, t4.jx_price, t4.yb_price, t4.jds_price, + t4.jd_lock_time, t4.ebai_lock_time, t4.mtwm_lock_time, t4.jx_lock_time, t4.yb_lock_time, t4.jds_lock_time, + t4.status_sale_begin, t4.status_sale_end, t4.stock, t4.mt_ladder_box_price, + t6.mid_unit_price real_mid_unit_price, + t7.unit_price audit_unit_price,t8.name categoryName + ` + sql + if isHighPrice || priceType != 0 { + sql += " , t4.unit_price DESC LIMIT 99" + } + var tmpList []*tGetStoresSkusInfo + beginTime := time.Now() + if err = dao.GetRowsTx(txDB, &tmpList, sql, sqlParams...); err != nil { + dao.Rollback(db, txDB) + return nil, err + } + if isBySku { + skuNamesInfo.TotalCount = dao.GetLastTotalRowCount2(db, txDB) + } + dao.Commit(db, txDB) + globals.SugarLogger.Debugf("GetStoresSkusNew get result2:%v", time.Now().Sub(beginTime)) + storeNameMap := make(map[int64]*dao.StoreSkuNameExt) + for _, v := range tmpList { + var storeName *dao.StoreSkuNameExt + index := jxutils.Combine2Int(v.StoreID, v.ID) + if isBySku || storeNameMap[index] == nil { + storeName = &dao.StoreSkuNameExt{ + StoreID: v.StoreID, + StoreName: v.StoreName, + SkuName: v.SkuName, + UnitPrice: v.UnitPrice, + PayPercentage: v.PayPercentage, + RealMidUnitPrice: v.RealMidUnitPrice, + YbSkuName: v.YbSkuName, + AuditUnitPrice: v.AuditUnitPrice, + } + if !isBySku { + storeNameMap[index] = storeName + } + skuNamesInfo.SkuNames = append(skuNamesInfo.SkuNames, storeName) + } else { + storeName = storeNameMap[index] + } + storeName.Skus = append(storeName.Skus, &v.StoreSkuExt) + } + if err == nil { + if isFocus { + if isSaleInfo { + beginTime := time.Now() + err = updateSaleInfo4StoreSkuName(ctx, db, storeIDs, skuIDs, params, skuNamesInfo, offset, pageSize) + globals.SugarLogger.Debugf("GetStoresSkusNew updateSaleInfo4StoreSkuName:%v", time.Now().Sub(beginTime)) + } + if err == nil { + if true { //!(offset == 0 && pageSize == model.UnlimitedPageSize) { + storeIDs, skuIDs = GetStoreAndSkuIDsFromInfo(skuNamesInfo) + } + beginTime := time.Now() + err = dao.UpdateActPrice4StoreSkuNameNew(db, storeIDs, skuIDs, skuNamesInfo, actVendorID) + globals.SugarLogger.Debugf("GetStoresSkusNew updateActPrice4StoreSkuName:%v", time.Now().Sub(beginTime)) + } + } else { + err = updateUnitPrice4StoreSkuNameNew(db, skuNamesInfo) + } + } + // globals.SugarLogger.Debug(utils.Format4Output(skuNamesInfo, false)) + return skuNamesInfo, err +} + func GetStoreAndSkuIDsFromInfo(skuNamesInfo *dao.StoreSkuNamesInfo) (storeIDs, skuIDs []int) { storeIDMap := make(map[int]int) skuIDMap := make(map[int]int) diff --git a/business/jxstore/cms/store_sku_check.go b/business/jxstore/cms/store_sku_check.go index 39eca8704..ff4bc0d3a 100644 --- a/business/jxstore/cms/store_sku_check.go +++ b/business/jxstore/cms/store_sku_check.go @@ -39,10 +39,11 @@ const ( DatAanalyse4 = "商品可售状态不同 " DatAanalyse5 = "京西商品库没有,平台商品库有 " DatAanalyse6 = "京西商品库有,平台商品库没有" - DatAanalyse7 = "同步状态异常" + DatAanalyse7 = "" //update by hang 这个提示毫无意义 并未做任何同步操作获取错误码 纯粹因为有不同才会拼接 DatAanalyse8 = "平台门店未关注或平台门店商品库存为0,应添加对应的平台门店商品" DatAanalyse9 = "平台门店价格与京西商品库价格不一致" DatAanalyse10 = "平台商品的VendorSkuID与京西的VendorSkuID不一致" + DatAanalyse11 = "平台商品的类别与京西的类别不一致" ) var ( @@ -71,6 +72,8 @@ var ( "平台可售状态", "京西价格", "平台价格", + "京西商品类别", + "平台商品类别", "数据分析", } @@ -134,22 +137,24 @@ type DepotDiffData struct { } type DiffData struct { - JxStoreID string `json:"京西门店ID"` - VendorStoreID string `json:"平台门店ID"` - VendorStoreName string `json:"门店名"` - SkuID string `json:"SkuID"` - MtwmID string `json:"京西美团外卖ID"` - EbaiID string `json:"京西饿百ID"` - SyncStatus string `json:"同步状态"` - ToBeCreate string `json:"待创建"` - ToBeDel string `json:"待删除"` - JxSkuName string `json:"京西商品名"` - VendorSkuName string `json:"平台商品名"` - JxStatus string `json:"京西可售状态"` - VendorStatus string `json:"平台可售状态"` - JxSkuPrice string `json:"京西价格"` /*哇,不能小写,不然会搞事情*/ - VendorPrice string `json:"平台价格"` - DatAanalyse string `json:"数据分析"` + JxStoreID string `json:"京西门店ID"` + VendorStoreID string `json:"平台门店ID"` + VendorStoreName string `json:"门店名"` + SkuID string `json:"SkuID"` + MtwmID string `json:"京西美团外卖ID"` + EbaiID string `json:"京西饿百ID"` + SyncStatus string `json:"同步状态"` + ToBeCreate string `json:"待创建"` + ToBeDel string `json:"待删除"` + JxSkuName string `json:"京西商品名"` + VendorSkuName string `json:"平台商品名"` + JxStatus string `json:"京西可售状态"` + VendorStatus string `json:"平台可售状态"` + JxSkuPrice string `json:"京西价格"` /*哇,不能小写,不然会搞事情*/ + VendorPrice string `json:"平台价格"` + JxCategoryName string `json:"京西商品类别"` + VendorCategoryName string `json:"平台商品类别"` + DatAanalyse string `json:"数据分析"` } type StatisticData struct { @@ -354,6 +359,12 @@ func IsSkuCanSale(saleStatus int) bool { //storeIDStr 京西商家id ,vendorStoreID 平台商家id ,isJd 京东比较的标记 0不是,1是 func CompareJxAndVendor(vendorID int, storeIDStr, vendorStoreID, storeName string, filterJxSkuInfoMap map[int]*dao.StoreSkuNameExt, filterVendorSkuInfoMap map[int]*partner.SkuNameInfo, isJd int) { //utils.Writelog("进入 CompareJxAndVendor 方法") + var vendorMap map[string]string + baseapi.SugarLogger.Debugf("-----------------------------------------------------------------------------------------------------") + if vendorID == 0 { + //TO DO 进行查询 select count(*) from sku_vendor_category where vendor_id=0; 一共3047 数据一次connection查询出来 组成一个map {categoryID,name} + vendorMap = getJDVendorCategoryMap() + } for skuID, jxSkuInfo := range filterJxSkuInfoMap { skuIDStr := utils.Int2Str(skuID) /*写京西skuIDStr*/ @@ -372,6 +383,9 @@ func CompareJxAndVendor(vendorID int, storeIDStr, vendorStoreID, storeName strin /*美团编码*/ mtwmid := jxSkuInfo.Skus[0].MtwmID //jxSkuPrice := strconv.Itoa(jxSkuInfo.Skus[0].JxPrice) + /*商品类名*/ + jxCategoryName := jxSkuInfo.Skus[0].CategoryName + //fmt.Println(jxCategoryName) vendorSkuInfo := filterVendorSkuInfoMap[skuID] var status int8 if vendorID == model.VendorIDMTWM { @@ -386,7 +400,19 @@ func CompareJxAndVendor(vendorID int, storeIDStr, vendorStoreID, storeName strin toBeDel := GetBoolName(model.IsSyncStatusNeedDelete(status)) if vendorSkuInfo != nil { + if vendorID == 0 && len(vendorMap) != 0 { //进行转换 + catID := []string{} + categoryName := vendorMap[vendorSkuInfo.VendorCatIDList[len(vendorSkuInfo.VendorCatIDList)-1]] + catID = append(catID, categoryName) + vendorSkuInfo.VendorCatIDList = catID + } + vendorSkuDetailName := vendorSkuInfo.SkuList[0].SkuName + vendorCategoryName := "" + if len(vendorSkuInfo.VendorCatIDList) != 0 { + vendorCategoryName = vendorSkuInfo.VendorCatIDList[len(vendorSkuInfo.VendorCatIDList)-1] + } + fmt.Println(vendorCategoryName) vendorSkuSaleStatusName := GetSkuSaleStatusName(vendorSkuInfo.SkuList[0].Status + 3) /* 供货商价格 */ vendorPrice := fmt.Sprintf("%.2f", float64(vendorSkuInfo.SkuList[0].StoreSkuInfo.VendorPrice)/float64(100)) @@ -402,6 +428,7 @@ func CompareJxAndVendor(vendorID int, storeIDStr, vendorStoreID, storeName strin isPriceDiff := vendorPrice != jxSkuPrice //utils.Writelog("isSaleStatusDiff:" + strconv.FormatBool(isSaleStatusDiff)) //utils.Writelog("isNameDiff:" + strconv.FormatBool(isNameDiff)) + isCategoryDiff := vendorCategoryName != jxCategoryName if jxSkuDetailName != "" && vendorSkuDetailName != "" && strings.Contains(jxSkuDetailName, vendorSkuDetailName) { isNameDiff = false } @@ -416,18 +443,23 @@ func CompareJxAndVendor(vendorID int, storeIDStr, vendorStoreID, storeName strin if isPriceDiff { reason += DatAanalyse9 } + if vendorID != 3 { //饿百平台查询获取到的商品信息是没有类别的 因此单独需要判断 + if isCategoryDiff { + reason += DatAanalyse11 + } + } if IdMark { reason += DatAanalyse10 } if status != model.SkuStatusDontSale { reason += DatAanalyse7 } - outPutData := DiffData{storeIDStr, vendorStoreID, storeName, skuIDStr, mtwmid, ebaiid, syncStatus, toBeCreate, toBeDel, jxSkuDetailName, vendorSkuDetailName, jxSkuSaleStatusName, vendorSkuSaleStatusName, jxSkuPrice, vendorPrice, reason} + outPutData := DiffData{storeIDStr, vendorStoreID, storeName, skuIDStr, mtwmid, ebaiid, syncStatus, toBeCreate, toBeDel, jxSkuDetailName, vendorSkuDetailName, jxSkuSaleStatusName, vendorSkuSaleStatusName, jxSkuPrice, vendorPrice, jxCategoryName, vendorCategoryName, reason} diffData.AppendData(vendorID, outPutData) } if !isSaleStatusDiff && !isNameDiff { if status != model.SkuStatusDontSale { - outPutData := DiffData{storeIDStr, vendorStoreID, storeName, skuIDStr, mtwmid, ebaiid, syncStatus, toBeCreate, toBeDel, jxSkuDetailName, vendorSkuDetailName, jxSkuSaleStatusName, vendorSkuSaleStatusName, jxSkuPrice, vendorPrice, DatAanalyse7} + outPutData := DiffData{storeIDStr, vendorStoreID, storeName, skuIDStr, mtwmid, ebaiid, syncStatus, toBeCreate, toBeDel, jxSkuDetailName, vendorSkuDetailName, jxSkuSaleStatusName, vendorSkuSaleStatusName, jxSkuPrice, vendorPrice, jxCategoryName, vendorCategoryName, DatAanalyse7} diffData.AppendData(vendorID, outPutData) } } @@ -444,7 +476,7 @@ func CompareJxAndVendor(vendorID int, storeIDStr, vendorStoreID, storeName strin if status != model.SkuStatusDontSale { reason += DatAanalyse7 } - outPutData := DiffData{storeIDStr, vendorStoreID, storeName, skuIDStr, mtwmid, ebaiid, syncStatus, toBeCreate, toBeDel, jxSkuDetailName, "", jxSkuSaleStatusName, "", jxSkuPrice, "", reason} + outPutData := DiffData{storeIDStr, vendorStoreID, storeName, skuIDStr, mtwmid, ebaiid, syncStatus, toBeCreate, toBeDel, jxSkuDetailName, "", jxSkuSaleStatusName, "", jxSkuPrice, "", jxCategoryName, "", reason} diffData.AppendData(vendorID, outPutData) } } @@ -460,7 +492,12 @@ func CompareJxAndVendor(vendorID int, storeIDStr, vendorStoreID, storeName strin jxSkuInfo := filterJxSkuInfoMap[skuID] /*平台有,京西没有*/ if jxSkuInfo == nil { - outPutData := DiffData{storeIDStr, vendorStoreID, "", "", storeName, skuIDStr, "", "", "", "", vendorSkuDetailName, "", vendorSkuSaleStatusName, "", vendorPrice, DatAanalyse1} + //update by hang 2022/4/12 映射bug + vendorCategoryName := "" + if len(vendorSkuInfo.VendorCatIDList) != 0 { + vendorCategoryName = vendorSkuInfo.VendorCatIDList[len(vendorSkuInfo.VendorCatIDList)-1] + } + outPutData := DiffData{storeIDStr, vendorStoreID, storeName, skuIDStr, "", "", "", "", "", "", vendorSkuDetailName, "", vendorSkuSaleStatusName, "", vendorPrice, "", vendorCategoryName, DatAanalyse1} diffData.AppendData(vendorID, outPutData) } } else { @@ -472,6 +509,35 @@ func CompareJxAndVendor(vendorID int, storeIDStr, vendorStoreID, storeName strin } } +type VendorCategory struct { + VendorCategoryID string `orm:"size(48);column(vendor_category_id)" json:"vendorCategoryID"` + Name string `orm:"size(255);index" json:"name"` +} + +// 获取京东类别映射 +func getJDVendorCategoryEntity() (vendorCategoryList []*VendorCategory, err error) { + db := dao.GetDB() + sql := ` + select vendor_category_id,name from sku_vendor_category where vendor_id=? + ` + var sqlParams []interface{} + sqlParams = append(sqlParams, 0) + err = dao.GetRows(db, &vendorCategoryList, sql, sqlParams...) + return vendorCategoryList, err +} + +//获取京东所有类别映射 +func getJDVendorCategoryMap() map[string]string { + result := make(map[string]string) + list, err := getJDVendorCategoryEntity() + if err == nil { + for _, v := range list { + result[v.VendorCategoryID] = v.Name + } + } + return result +} + func FilterJxDepotUnSaleSkuID() { db := dao.GetDB() filterJxDepotUnSaleSkuIds = filterJxDepotUnSaleSkuIds[0:0] @@ -963,7 +1029,8 @@ func TestDiff(ctx *jxcontext.Context, vendorIDList []int, storeIDList []int) { vendorID := vendorListValue.VendorID if partner.IsMultiStore(vendorID) { if multiFlag == false { - jxSkuInfoDataMulti, _ = GetStoreSkus(ctx, storeID, filterJxDepotUnSaleSkuIds, true, "", true, false, map[string]interface{}{}, 0, -1) + //jxSkuInfoDataMulti, _ = GetStoreSkus(ctx, storeID, filterJxDepotUnSaleSkuIds, true, "", true, false, map[string]interface{}{}, 0, -1) + jxSkuInfoDataMulti, _ = GetStoreSkus2(ctx, storeID, filterJxDepotUnSaleSkuIds, true, "", true, false, map[string]interface{}{}, 0, -1) /*重新计算价格*/ SetJxPrice(jxSkuInfoDataMulti, storeID, vendorID) filterJxSkuInfoMapMulti = GetFilterJxSkuInfoMap(jxSkuInfoDataMulti.SkuNames) //map[京西商品ID:StoreSkuNameExt] @@ -971,7 +1038,8 @@ func TestDiff(ctx *jxcontext.Context, vendorIDList []int, storeIDList []int) { } } else { if singleFlag == false { - jxSkuInfoDataSingle, _ = GetStoreSkus(ctx, storeID, nil, true, "", true, false, map[string]interface{}{}, 0, -1) + //jxSkuInfoDataSingle, _ = GetStoreSkus(ctx, storeID, nil, true, "", true, false, map[string]interface{}{}, 0, -1) + jxSkuInfoDataSingle, _ = GetStoreSkus2(ctx, storeID, nil, true, "", true, false, map[string]interface{}{}, 0, -1) /*重新计算价格*/ SetJxPrice(jxSkuInfoDataSingle, storeID, vendorID) filterJxSkuInfoMapSingle = GetFilterJxSkuInfoMap(jxSkuInfoDataSingle.SkuNames) //map[京西商品ID:StoreSkuNameExt] @@ -1166,13 +1234,15 @@ func CheckSkuDiffBetweenJxAndVendor(ctx *jxcontext.Context, vendorIDList []int, vendorID := vendorListValue.VendorID if partner.IsMultiStore(vendorID) { if multiFlag == false { - jxSkuInfoDataMulti, _ = GetStoreSkus(ctx, storeID, filterJxDepotUnSaleSkuIds, true, "", true, false, map[string]interface{}{}, 0, -1) + //jxSkuInfoDataMulti, _ = GetStoreSkus(ctx, storeID, filterJxDepotUnSaleSkuIds, true, "", true, false, map[string]interface{}{}, 0, -1) + jxSkuInfoDataMulti, _ = GetStoreSkus2(ctx, storeID, filterJxDepotUnSaleSkuIds, true, "", true, false, map[string]interface{}{}, 0, -1) filterJxSkuInfoMapMulti = GetFilterJxSkuInfoMap(jxSkuInfoDataMulti.SkuNames) //map[京西商品ID:StoreSkuNameExt] multiFlag = true } } else { if singleFlag == false { - jxSkuInfoDataSingle, _ = GetStoreSkus(ctx, storeID, nil, true, "", true, false, map[string]interface{}{}, 0, -1) + //jxSkuInfoDataSingle, _ = GetStoreSkus(ctx, storeID, nil, true, "", true, false, map[string]interface{}{}, 0, -1) + jxSkuInfoDataSingle, _ = GetStoreSkus2(ctx, storeID, nil, true, "", true, false, map[string]interface{}{}, 0, -1) filterJxSkuInfoMapSingle = GetFilterJxSkuInfoMap(jxSkuInfoDataSingle.SkuNames) //map[京西商品ID:StoreSkuNameExt] singleFlag = true } diff --git a/business/model/dao/store_sku.go b/business/model/dao/store_sku.go index 1b8e5db99..b41b22f6c 100644 --- a/business/model/dao/store_sku.go +++ b/business/model/dao/store_sku.go @@ -252,16 +252,16 @@ type StoreSkuVendorInfo struct { } type StoreSkuExt struct { - NameID int `orm:"column(name_id)" json:"nameID"` - SkuID int `orm:"column(sku_id)" json:"id"` - Comment string `orm:"size(255)" json:"comment"` - SkuCategoryID int `orm:"column(sku_category_id)" json:"categoryID"` - SkuSpecQuality float32 `json:"specQuality"` - SkuSpecUnit string `orm:"size(8)" json:"specUnit"` // 质量或容量 - Weight int `json:"weight"` // 重量/质量,单位为克,当相应的SkuName的SpecUnit为g或kg时,必须等于SpecQuality - SkuStatus int `json:"status"` - Stock int `json:"stock"` - + NameID int `orm:"column(name_id)" json:"nameID"` + SkuID int `orm:"column(sku_id)" json:"id"` + Comment string `orm:"size(255)" json:"comment"` + SkuCategoryID int `orm:"column(sku_category_id)" json:"categoryID"` + SkuSpecQuality float32 `json:"specQuality"` + SkuSpecUnit string `orm:"size(8)" json:"specUnit"` // 质量或容量 + Weight int `json:"weight"` // 重量/质量,单位为克,当相应的SkuName的SpecUnit为g或kg时,必须等于SpecQuality + SkuStatus int `json:"status"` + Stock int `json:"stock"` + CategoryName string `orm:"column(categoryName)"` BindCreatedAt time.Time `orm:"auto_now_add;type(datetime)" json:"createdAt"` BindUpdatedAt time.Time `orm:"auto_now;type(datetime)" json:"updatedAt"` BindLastOperator string `orm:"size(32)" json:"lastOperator"` // 最后操作员