package front import ( qu "app.yhyue.com/moapp/jybase/common" "app.yhyue.com/moapp/jybase/encrypt" elastic "app.yhyue.com/moapp/jybase/es" "app.yhyue.com/moapp/jybase/redis" "app.yhyue.com/moapp/jypkg/common/src/qfw/util/bidsearch" "app.yhyue.com/moapp/jypkg/public" "encoding/json" "fmt" "github.com/gogf/gf/v2/util/gconv" "jy/src/jfw/config" "log" "strconv" "strings" "sync" "time" "net/http" "app.yhyue.com/moapp/jybase/date" "app.yhyue.com/moapp/jybase/go-xweb/httpsession" ) const ( //企业主体库身份类型区分 sql传值 IdentityTypeBuyer = 0 // 采购单位 IdentityTypeWinner = 1 // 中标单位 ) type KeyType struct { Name string `json:"name"` Url string `json:"url"` SeedData []KeyType `json:"seedData"` } // RegionAndInformationAndTender 1地域 2信息类型 3热门招标 func RegionAndInformationAndTender() map[string]interface{} { if bytes, err := redis.GetBytes(RedisNameNew, "regionAndInformationAndTender"); err == nil && bytes != nil { rData := map[string]interface{}{} if err := json.Unmarshal(*bytes, &rData); err != nil { log.Printf("[MANAGER-ERR]RegionAndInformationAndTender GetData Error %v \n", err) return nil } return rData } data := make(map[string]interface{}) for _, v := range []int{1, 2, 3} { data[fmt.Sprintf("labUrl_%d", v)] = GetLabUrl(v) //1地域 2信息类型 3热门招标 } if bytes, err := json.Marshal(data); err == nil && bytes != nil { _ = redis.PutBytes(RedisNameNew, "regionAndInformationAndTender", &bytes, 2*60*60) } return data } func GetHotIndustry() (rData []map[string][]map[string]interface{}) { if bytes, err := redis.GetBytes(RedisNameNew, "pcIndexHotIndustry"); err == nil && bytes != nil { rData = []map[string][]map[string]interface{}{} if err := json.Unmarshal(*bytes, &rData); err != nil { log.Printf("[MANAGER-ERR]pcIndexHotIndustry GetData Error %v \n", err) return nil } } rData = getkeysMap() //热门行业 if bytes, err := json.Marshal(rData); err == nil && bytes != nil { _ = redis.PutBytes(RedisNameNew, "pcIndexHotIndustry", &bytes, RedisTimeout) } return rData } // 最新更新的200中标企业 func GetWinnerInfo() (data []*BuyerList) { // 取缓存 cache, err := GetHotCache(config.HotWinnerConfig.CacheKey) if err == nil && cache != nil && len(cache) > 0 { return cache } // 没取到缓存查数据 rs := GetHotWinnerBuyer(IdentityTypeWinner, config.HotWinnerConfig.Limit) //关联中标企业 if rs == nil || len(rs) == 0 { return } for _, v := range rs { var vs BuyerList vs.Name = qu.InterfaceToStr(v["name"]) vs.Url = qu.InterfaceToStr(v["url"]) data = append(data, &vs) } // 存缓存 go PutHotCache(config.HotWinnerConfig.CacheKey, config.HotWinnerConfig.CacheTimeout, data) return } // PutHotCache 热门采购单位、中标单位存缓存 func PutHotCache(redisKey string, redisTimeout int, list []*BuyerList) { b, err := json.Marshal(list) if err != nil { log.Printf("保存缓存 序列化异常,data:%s,err:%s\n", list, err.Error()) return } if err = redis.PutBytes("seoCache", redisKey, &b, redisTimeout); err != nil { log.Printf("保存缓存 redis 异常,key:%s,err:%s\n", redisKey, err.Error()) } } // GetHotCache 热门采购单位、中标单位取缓存 func GetHotCache(redisKey string) (list []*BuyerList, err error) { redisByte, err := redis.GetBytes("seoCache", redisKey) if err != nil || redisByte == nil || len(*redisByte) == 0 { return list, err } err = json.Unmarshal(*redisByte, &list) if err != nil { log.Println(fmt.Sprintf("读取缓存 序列化异常,err:%s", err.Error())) return nil, err } return list, nil } // 获取最新的中标单位 // identityType : 0 采购单位 1-中标单位 // limit: 数量 func getEntBaseInfo(identityType, limit int) *[]map[string]interface{} { q := "SELECT company_id AS id,name,name_id FROM dws_f_ent_baseinfo WHERE company_id !='' and company_id is not null AND (identity_type &(1 << ?)) > 0 order by latest_time desc limit ?" return public.GlobalCommonMysql.SelectBySql(q, identityType, limit) } func GetHotWinnerBuyer(identityType, limit int) []map[string]interface{} { isWinner := identityType == 1 queryTotal := gconv.Int(gconv.Float64(limit) * 1.5) var querySql string if isWinner { querySql = fmt.Sprintf(`{"query": {"bool": {"must": [{"exists": {"field": "s_winner"}},{"exists": {"field": "entidlist"}}],"must_not":[{"term":{"entidlist":"-"}}]}},"_source":["buyer","s_winner","entidlist"],"sort":[{"lasttime": "desc"}],"size": %d}`, queryTotal) } else { querySql = fmt.Sprintf(`{"query": {"bool": {"must": [{"exists": {"field": "buyer"}}]}},"_source":["buyer","s_winner","entidlist"],"sort":[{"lasttime": "desc"}],"size": %d}`, queryTotal) } getData := elastic.GetNoLimit("projectset", "projectset", querySql) var finalList []map[string]interface{} if getData != nil && len(*getData) > 0 { queryMap := make(map[string]bool) if isWinner { //采购关联企业 校验正确性 var queryArr []string for _, v := range *getData { if len(queryArr) < queryTotal { for _, name := range gconv.Strings(v["entidlist"]) { if name == "" || name == "-" { continue } if queryMap[name] { continue } queryArr = append(queryArr, name) queryMap[name] = true if len(queryArr) == queryTotal { break } } } } finalList = getWinnerSeoIdByName(queryArr...) } else { var queryArr []string for _, v := range *getData { buyerName := gconv.String(v["buyer"]) if queryMap[buyerName] { continue } queryArr = append(queryArr, buyerName) queryMap[buyerName] = true } finalList = getBuyerSeoIdByName(queryArr...) } } if len(finalList) > limit { finalList = finalList[:limit] } return finalList } // 根据企业名称获取seoid // query: company_name 根据名字匹配 // query: _id 根据entid匹配 func getWinnerSeoIdByName(winners ...string) (res []map[string]interface{}) { if len(winners) == 0 { return } winnerRes := elastic.Get("qyxy", "qyxy", fmt.Sprintf(`{"query":{"terms":{"_id":["%s"]}},"_source":[%s],"size":%d}`, strings.Join(winners, `","`), `"nseo_id","company_name"`, len(winners))) if winnerRes != nil && len(*winnerRes) > 0 { for _, m := range *winnerRes { name := gconv.String(m["company_name"]) sid := gconv.String(m["nseo_id"]) if name != "" && sid != "" { res = append(res, map[string]interface{}{ "name": name, "seoId": sid, "url": fmt.Sprintf("/qy/%s.html", sid), }) } } } return } // 根据企业名称获取seoid // query: company_name 根据名字匹配 // query: _id 根据entid匹配 func getWinnerSeoIdByNameNew(query string, fullData bool, winners ...string) (res []map[string]interface{}) { if len(winners) == 0 { return } var fields string = `"nseo_id","company_name","_id"` if fullData { fields = `"nseo_id","company_name","legal_person","capital","company_address","company_status"` } winnerMap := map[string]map[string]interface{}{} winnerRes := elastic.GetNoLimit(qyxy, qyxy, fmt.Sprintf(`{"query":{"terms":{"%s":["%s"]}},"_source":[%s],"size":%d}`, query, strings.Join(winners, `","`), fields, len(winners))) if winnerRes != nil && len(*winnerRes) > 0 { for _, m := range *winnerRes { name := gconv.String(m["company_name"]) sid := gconv.String(m["nseo_id"]) entId := gconv.String(m["_id"]) if name != "" && sid != "" && entId != "" { row := map[string]interface{}{ "name": name, "seoId": sid, "url": fmt.Sprintf("/qy/%s.html", sid), } if fullData { row["legal_person"] = m["legal_person"] row["capital"] = m["capital"] //if dataStamp := gconv.Int64(m["establish_date"]); dataStamp > 0 { // row["establish_date"] = gtime.New(dataStamp).Format("Y-m-d") //} //row["company_phone"] = m["company_phone"] row["address"] = m["company_address"] if state := gconv.String(m["company_status"]); state != "" { row["company_status"] = strings.Split(state, "(")[0] } } winnerMap[entId] = row } } } for _, winner := range winners { if m := winnerMap[winner]; m != nil { res = append(res, m) } } return } // 根据采购单位名字获取seoid func getBuyerSeoIdByNameNew(fullData bool, buyers ...string) (res []map[string]interface{}) { if len(buyers) == 0 { return } var fields string = `"seo_id","name"` if fullData { fields = `"seo_id","name","province","city","buyerclass"` } buyerMap := map[string]map[string]interface{}{} buyerRes := elastic.GetNoLimit("buyer", "buyer", fmt.Sprintf(`{"query":{"terms":{"buyer_name":["%s"]}},"_source":[%s],"size":%d}`, strings.Join(buyers, `","`), fields, len(buyers))) if buyerRes != nil && len(*buyerRes) > 0 { for _, m := range *buyerRes { name := gconv.String(m["name"]) sid := gconv.String(m["seo_id"]) if name != "" && sid != "" { row := map[string]interface{}{ "name": name, "seoId": sid, "url": fmt.Sprintf("/dw/%s.html", sid), } if fullData { row["buyerclass"] = m["buyerclass"] row["area"] = m["province"] row["city"] = m["city"] } buyerMap[name] = row } } } for _, buyer := range buyers { if m := buyerMap[buyer]; m != nil { res = append(res, m) } } return } // 根据采购单位名字获取seoid func getBuyerSeoIdByName(buyer ...string) (res []map[string]interface{}) { if len(buyer) == 0 { return } buyerRes := elastic.GetNoLimit("buyer", "buyer", fmt.Sprintf(`{"query":{"terms":{"buyer_name":["%s"]}},"_source":[%s],"size":%d}`, strings.Join(buyer, `","`), `"seo_id","name"`, len(buyer))) if buyerRes != nil && len(*buyerRes) > 0 { for _, m := range *buyerRes { name := gconv.String(m["name"]) sid := gconv.String(m["seo_id"]) if name != "" && sid != "" { res = append(res, map[string]interface{}{ "name": name, "seoId": sid, "url": fmt.Sprintf("/dw/%s.html", sid), }) } } } return } // ContentRecommendation 实用内容推荐 func ContentRecommendation() []KeyType { if bytes, err := redis.GetBytes(RedisNameNew, "contentRecommendation"); err == nil && bytes != nil { var rData []KeyType log.Println() if err := json.Unmarshal(*bytes, &rData); err != nil { log.Printf("[MANAGER-ERR]contentRecommendation GetData Error %v \n", err) return nil } return rData } columnCode, _ := config.Sysconfig["columnCode"].(map[string]interface{}) jySchoolCode := qu.InterfaceToStr(columnCode["招投标攻略"]) industryInfoCode := qu.InterfaceToStr(columnCode["行业资讯"]) industryInfoUrl, _ := config.Sysconfig["industryInfoUrl"].(map[string]interface{}) jySchoolUrl, _ := config.Sysconfig["jySchoolUrl"].(map[string]interface{}) column, ok := mongodb.Find("column", map[string]interface{}{"$or": []map[string]interface{}{ {"pid": "ztbgl"}, {"pid": "hyzx"}, {"pid": "bzzx"}, }}, `{"i_order":1}`, "", false, -1, -1) dataMap := make(map[string][]KeyType) if ok && column != nil && len(*column) > 0 { for _, v := range *column { pid := qu.InterfaceToStr(v["pid"]) code := qu.InterfaceToStr(v["s_columncode"]) var v1 KeyType v1.Name = qu.InterfaceToStr(v["s_columnname"]) if pid == jySchoolCode { v1.Url = fmt.Sprintf(qu.InterfaceToStr(jySchoolUrl["towUrl"]), code) } else if pid == industryInfoCode { v1.Url = fmt.Sprintf(qu.InterfaceToStr(industryInfoUrl["towUrl"]), code) } else if pid == "bzzx" { v1.Url = fmt.Sprintf("/helpCenter/catalog/%s", code) } dataMap[pid] = append(dataMap[pid], v1) } } var data []KeyType for _, v := range []string{jySchoolCode, industryInfoCode, "bzzx"} { if v1, ok1 := dataMap[v]; ok1 && v1 != nil { var d KeyType switch v { case jySchoolCode: d.Name = "招投标攻略" d.Url = qu.InterfaceToStr(jySchoolUrl["homeUrl"]) d.SeedData = v1 case industryInfoCode: d.Name = "行业资讯" d.Url = qu.InterfaceToStr(industryInfoUrl["homeUrl"]) d.SeedData = v1 case "bzzx": d.Name = "帮助中心" d.Url = "/helpCenter/index" d.SeedData = v1 } data = append(data, d) } } if bytes, err := json.Marshal(data); err == nil && bytes != nil { _ = redis.PutBytes(RedisNameNew, "contentRecommendation", &bytes, 12*60*60) } return data } type Signal struct { Name string `json:"name"` Url string `json:"url"` UnLoginUrl string `json:"unLoginUrl"` Data []map[string]interface{} `json:"data"` } // 推荐标讯 func RecommendationBeacon() []Signal { if bytes, err := redis.GetBytes(RedisNameNew, "recommendationBeacon"); err == nil && bytes != nil { var rData []Signal if err := json.Unmarshal(*bytes, &rData); err != nil { log.Printf("[MANAGER-ERR]recommendationBeacon GetData Error %v \n", err) return nil } return rData } var ( now = time.Now() startTime = fmt.Sprint(time.Date(now.Year(), now.Month(), now.Day()-7, now.Hour(), now.Minute(), now.Second(), 0, time.Local).Unix()) //最近7天 endTime = fmt.Sprint(now.Unix()) publishTime = fmt.Sprintf("%s_%s", startTime, endTime) ) sy := sync.RWMutex{} wg := sync.WaitGroup{} var data, dataArr []Signal infoType := qu.ObjToMap(config.Seoconfig["infoTypeToLetter"]) for _, v := range []string{"招标预告", "招标公告", "招标结果", "招标信用信息"} { wg.Add(1) go func(vst string) { defer wg.Done() var ( list []map[string]interface{} ) _, _, lists := bidsearch.GetPcBidSearchData("", "", "", publishTime, vst, "", "", "", "", "", "", "", "", 1, false, nil, bidSearch_field_1, "", false, false, "", 8, "") if lists != nil { for _, v1 := range *lists { v1["_id"] = encrypt.EncodeArticleId2ByCheck(v1["_id"].(string)) delete(v1, "toptype") delete(v1, "s_subscopeclass") tmpdate := v1["publishtime"] v1["publishtime"] = qu.Int64All(tmpdate.(float64)) if v1["budget"] != nil { v1["budget"] = ConversionMoeny(v1["budget"]) } else if v1["bidamount"] != nil { v1["budget"] = ConversionMoeny(v1["bidamount"]) } } list = *lists } var d Signal d.Name = vst d.UnLoginUrl = fmt.Sprintf("/list/stype/%s.html", (*infoType)[vst]) d.Url = fmt.Sprintf("/jylab/supsearch/index.html?subtype=%s", vst) d.Data = list sy.Lock() dataArr = append(dataArr, d) sy.Unlock() }(v) } wg.Wait() for _, v := range []string{"招标预告", "招标公告", "招标结果", "招标信用信息"} { for _, v1 := range dataArr { if v == v1.Name { data = append(data, v1) } } } if bytes, err := json.Marshal(data); err == nil && bytes != nil { _ = redis.PutBytes(RedisNameNew, "recommendationBeacon", &bytes, 5*60) } return data } type BuyerList struct { Name string `json:"name"` Url string `json:"url"` } // 热门采购单位 func HotBuyerList() []*BuyerList { // 取缓存 cache, err := GetHotCache(config.HotBuyerConfig.CacheKey) if err == nil && cache != nil && len(cache) > 0 { return cache } // 查数据 //data := getEntBaseInfo(IdentityTypeBuyer, config.HotBuyerConfig.Limit) data := GetHotWinnerBuyer(IdentityTypeBuyer, config.HotBuyerConfig.Limit) if data == nil || len(data) == 0 { return nil } var buyerList []*BuyerList for _, b := range data { name := qu.ObjToString(b["name"]) url := qu.InterfaceToStr(b["url"]) if name != "" && url != "" { //idEncode := encrypt.EncodeArticleId2ByCheck(buyerId) buyerList = append(buyerList, &BuyerList{ Name: name, Url: url, }) } } //存缓存 go PutHotCache(config.HotBuyerConfig.CacheKey, config.HotBuyerConfig.CacheTimeout, buyerList) return buyerList } func GetIncludedInfo() map[string]interface{} { if bytes, err := redis.GetBytes(RedisNameNew, "jyIncludedInfo"); err == nil && bytes != nil { rData := map[string]interface{}{} if err := json.Unmarshal(*bytes, &rData); err != nil { log.Printf("[MANAGER-ERR]jyIncludedInfo GetData Error %v \n", err) return nil } return rData } data := public.BaseMysql.SelectBySql(`select bid,project,ent,buyer,bid_day_update,bid_field,field_accuracy,create_time from included_info order by create_time desc limit 1`) if data == nil || len(*data) <= 0 { return nil } info := (*data)[0] //招标信息的数值 bid := qu.Int64All(info["bid"]) Bid, BidUnit := formdataNum(bid) //招标采购项目的数值 project := qu.Int64All(info["project"]) Project, ProjectUnit := formdataNum(project) //企业数据库的数值 ent := qu.Int64All(info["ent"]) Ent, EntUnit := formdataNum(ent) //采购单位库的数值 buyer := qu.Int64All(info["buyer"]) Buyer, BuyerUnit := formdataNum(buyer) //每日更新招标信息的数值 bid_day_update := qu.Int64All(info["bid_day_update"]) BidDayUpdate, BidDayUpdateUnit := formdataNum(bid_day_update) mdata, ok := public.MQFW.Find("swordfish_index", map[string]interface{}{ "i_push": map[string]interface{}{ "$exists": true, }, }, `{"_id":-1}`, `{"i_push":1}`, false, 0, 1) i_push := 0 if mdata != nil && ok && len(*mdata) > 0 { swordData := (*mdata)[0] i_push = qu.IntAll(swordData["i_push"]) } Push, PushUnit := formdataNum(int64(i_push)) m := map[string]interface{}{ "bid": Bid, "bidUnit": BidUnit, "project": Project, "projectUnit": ProjectUnit, "ent": Ent, "entUnit": EntUnit, "buyer": Buyer, "buyerUnit": BuyerUnit, "bidDayUpdate": BidDayUpdate, "bidDayUpdateUnit": BidDayUpdateUnit, "push": Push, "pushUnit": PushUnit, } if bytes, err := json.Marshal(m); err == nil && bytes != nil { _ = redis.PutBytes(RedisNameNew, "jyIncludedInfo", &bytes, 2*60*60) } return m } func NewIndexbids(session *httpsession.Session, r *http.Request) []map[string]interface{} { if bytes, err := redis.GetBytes(RedisNameNew, "pcIndexNewBids"); err == nil && bytes != nil { rData := []map[string]interface{}{} if err := json.Unmarshal(*bytes, &rData); err != nil { log.Printf("[MANAGER-ERR]jyNewIndexbids GetData Error %v \n", err) return rData } return rData } /* userInfo := jy.GetVipState(session, *config.Middleground, "") so := NewSearchOptimize("", "", "", "", "招标预告,招标公告,招标结果,招标信用信息", "", "", "title", "", "", "", "", "", "", "", "", "", "PC", "", 0, 50, 0, 0, 0, *userInfo, true, r) so.DefaultSearchParamsAuto() //缓存数据 _, total, _ := so.GetBidSearchList(true) data.Count = total */ // p397 收回查看拟建权限 var ( now = time.Now() startTime = fmt.Sprint(time.Date(now.Year(), now.Month(), now.Day()-7, now.Hour(), now.Minute(), now.Second(), 0, time.Local).Unix()) //最近7天 endTime = fmt.Sprint(now.Unix()) publishTime = fmt.Sprintf("%s_%s", startTime, endTime) ) _, _, lists := bidsearch.GetPcBidSearchData("", "", "", publishTime, "招标预告,招标公告,招标结果,招标信用信息", "", "", "", "", "", "", "", "", 1, false, nil, bidSearch_field_1, "", false, false, "", 8, "") if lists != nil { for _, v1 := range *lists { v1["_id"] = encrypt.EncodeArticleId2ByCheck(v1["_id"].(string)) delete(v1, "toptype") delete(v1, "s_subscopeclass") tmpdate := v1["publishtime"] v1["publishtime"] = time.Unix(qu.Int64All(tmpdate.(float64)), 0).Format(date.Date_Short_Layout) if v1["budget"] != nil { v1["budget"] = ConversionMoeny(v1["budget"]) } else if v1["bidamount"] != nil { v1["budget"] = ConversionMoeny(v1["bidamount"]) } } if bytes, err := json.Marshal(*lists); err == nil && bytes != nil { _ = redis.PutBytes(RedisNameNew, "pcIndexNewBids", &bytes, 5*60) } return *lists } return nil } // 格式输出数据 // 亿亿、万亿、亿、万 只有一位的时候保留1位小数点 两位及以上不保留 1.1亿 11亿 func formdataNum(num int64) (floatNum float64, unit string) { s_num := strconv.Itoa(int(num)) len_m := len(s_num) m := "" indexArr := []int{17, 13, 9, 5} unitArr := []string{"亿亿", "万亿", "亿", "万"} for k, v := range indexArr { if len_m > v { if qu.IntAll(s_num[len_m-(v-1):len_m-(v-2)]) >= 5 { if qu.IntAll(s_num[0:len_m-(v-1)])+1 == 10 { //满10 进 1 m1, _ := strconv.Atoi(s_num[0 : len_m-(v-1)]) m = strconv.Itoa(m1 + 1) } else { //满 万 进1 单位 if qu.IntAll(s_num[0:len_m-(v-1)])+1 == 10000 { m = "1" unit = unitArr[k-1] } else { m = strconv.Itoa(qu.IntAll(s_num[0:len_m-(v-1)]) + 1) } } // log.Println("m1:", m) } else { m = s_num[0 : len_m-(v-1)] // log.Println("m2:", m) } } else if len_m == v { // if qu.IntAll(s_num[len_m-(v-2):len_m-(v-3)]) >= 5 { m = s_num[0 : len_m-(v-1)] //满10 进 1 if qu.IntAll(s_num[len_m-(v-1):len_m-(v-2)])+1 == 10 { m1, _ := strconv.Atoi(s_num[0 : len_m-(v-1)]) m = strconv.Itoa(m1 + 1) } else { m += "." + strconv.Itoa(qu.IntAll(s_num[len_m-(v-1):len_m-(v-2)])+1) } // log.Println("m3:", m) } else { m = s_num[0 : len_m-(v-1)] m += "." + s_num[len_m-(v-1):len_m-(v-2)] // log.Println("m4:", m) } } if m != "" { if unit == "" { unit = unitArr[k] } break } } if m == "" { m = s_num } //string 转float floatNum, _ = strconv.ParseFloat(m, 64) return floatNum, unit }