dataServiceArea.go 10.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343
  1. package front
  2. import (
  3. "app.yhyue.com/moapp/jybase/common"
  4. "app.yhyue.com/moapp/jybase/redis"
  5. "app.yhyue.com/moapp/jypkg/public"
  6. "encoding/json"
  7. "fmt"
  8. //_ "github.com/gogf/gf/contrib/drivers/clickhouse/v2"
  9. "github.com/gogf/gf/v2/frame/g"
  10. "github.com/gogf/gf/v2/os/gctx"
  11. "github.com/gogf/gf/v2/util/gconv"
  12. "jy/src/jfw/config"
  13. )
  14. // HotIndustryAndRegion 热门行业/地区年度招标趋势
  15. func HomeBiddingTrends() []config.IndustryTrend {
  16. return config.IndustryTrendConfig
  17. }
  18. type (
  19. KeyWordSiteRoot struct {
  20. SiteCodeMap map[string]*KeyWordSiteNode //省份直辖市简称对照
  21. SiteArr []*KeyWordSiteNode
  22. }
  23. KeyWordSiteNode struct {
  24. Code string `json:"code" doc:"代码"`
  25. Alias string `json:"alias" doc:"名称"`
  26. AreaKeyWord string `json:"areaKeyword" doc:"省份关键词"`
  27. CityKeyWord string `json:"cityKeyword" doc:"城市关键词"`
  28. CitySpecialKeyWord string `json:"citySpecialKeyword" doc:"直辖市关键词"`
  29. }
  30. KeyWordSiteShow struct {
  31. Code string `json:"code" doc:"代码"`
  32. Name string `json:"name" doc:"名称"`
  33. //KeyWord string `json:"keyWord" doc:"对应关键词"`
  34. }
  35. argument struct {
  36. Name string
  37. Url string
  38. }
  39. )
  40. var (
  41. siteCodeMap map[string]*KeyWordSiteNode
  42. specialArea = map[string]bool{"北京": true, "上海": true, "天津": true, "重庆": true}
  43. )
  44. func init() {
  45. siteCodeMap = make(map[string]*KeyWordSiteNode)
  46. res, err := g.DB().Query(gctx.New(), `SELECT * FROM seo_siteKeywords_splicing order by site_code asc`)
  47. if err == nil && len(res.List()) > 0 {
  48. for _, m := range res.List() {
  49. node := &KeyWordSiteNode{
  50. Code: fmt.Sprintf("S%s", gconv.String(m["site_code"])),
  51. Alias: gconv.String(m["alias"]),
  52. AreaKeyWord: gconv.String(m["area"]),
  53. CityKeyWord: gconv.String(m["city"]),
  54. CitySpecialKeyWord: gconv.String(m["city_special"]),
  55. }
  56. siteCodeMap[node.Code] = node
  57. }
  58. }
  59. }
  60. // 政府招标
  61. func GovernmentTender(number int) []argument {
  62. redisKey := "governmentTender"
  63. redisData := redis.Get(RedisNameNew, redisKey)
  64. if redisData != nil {
  65. if d, err := json.Marshal(redisData); err == nil {
  66. var signature []argument
  67. json.Unmarshal(d, &signature)
  68. return signature
  69. }
  70. }
  71. areaM := make(map[string]string)
  72. //省份
  73. areaMap, _ := config.Seoconfig["area"].(map[string]interface{})
  74. if areaMap != nil && len(areaMap) > 0 {
  75. for k, v := range areaMap {
  76. area := v.(map[string]interface{})
  77. name := common.ObjToString(area["NAME"])
  78. if name != "全国" && name != "香港" && name != "澳门" && name != "台湾" {
  79. areaM[name] = k
  80. }
  81. }
  82. }
  83. var (
  84. data []argument
  85. upperLimit int
  86. )
  87. siteCode := make(map[string]bool)
  88. for name, acronym := range areaM {
  89. upperLimit++
  90. if upperLimit > number {
  91. break
  92. }
  93. if len(siteCode) < len(siteCodeMap) {
  94. for code, node := range siteCodeMap {
  95. var tagName string
  96. if !siteCode[code] {
  97. if node.Alias != "" {
  98. tagName = node.Alias
  99. } else {
  100. tagName = common.If(specialArea[name], node.CitySpecialKeyWord, node.AreaKeyWord).(string)
  101. }
  102. data = append(data, argument{
  103. fmt.Sprintf("%s%s", name, tagName),
  104. fmt.Sprintf("/list/area/%s_%s", acronym, code),
  105. })
  106. siteCode[code] = true
  107. break
  108. }
  109. }
  110. } else {
  111. for code, node := range siteCodeMap {
  112. var tagName string
  113. if node.Alias != "" {
  114. tagName = node.Alias
  115. } else {
  116. tagName = common.If(specialArea[name], node.CitySpecialKeyWord, node.AreaKeyWord).(string)
  117. }
  118. data = append(data, argument{
  119. fmt.Sprintf("%s%s", name, tagName),
  120. fmt.Sprintf("/list/area/%s_%s", acronym, code),
  121. })
  122. break
  123. }
  124. }
  125. }
  126. redis.Put(RedisNameNew, redisKey, data, RedisTimeout)
  127. return data
  128. }
  129. /*
  130. const (
  131. PSearch_DecMust = `"bidstatus": ["中标","成交","合同","单一"]`
  132. query_bool_must = `{"terms": {%s}}`
  133. )
  134. var (
  135. industryMap map[string][]string
  136. )
  137. type ServiceRes struct {
  138. industry []industryRes
  139. }
  140. type industryRes struct {
  141. name string
  142. areas []areaRes
  143. }
  144. type areaRes struct {
  145. name string
  146. data []map[string]interface{}
  147. }
  148. type subzone struct {
  149. industry, province string
  150. }
  151. type marketBuckets struct {
  152. ProjectCount struct {
  153. DocCount int `json:"doc_count"`
  154. } `json:"project_count"`
  155. }
  156. func getQuarter(st int64) int {
  157. currentTime := time.Unix(st, 0)
  158. // 获取当前月份
  159. currentMonth := int(currentTime.Month())
  160. // 获取当前月份所属的季度
  161. return (currentMonth-1)/3 + 1
  162. }
  163. func init() {
  164. IndustryInit()
  165. BiddingTrendInit()
  166. }
  167. func BiddingTrend(st int64, et int64) {
  168. currentQuarter := getQuarter(st)
  169. for _, industry := range config.ServiceArea.Industry {
  170. ds := subzone{
  171. industry: industry,
  172. }
  173. for _, area := range config.ServiceArea.Area {
  174. ds.province = area
  175. res, _, _ := elastic.GetAggs("projectset", "projectset", GetCommonQuerySql(st, et, area, industry))
  176. if res != nil {
  177. thisRow := marketBuckets{}
  178. for name, object := range res {
  179. bArr, err := object.MarshalJSON()
  180. if len(bArr) == 0 || err != nil {
  181. break
  182. }
  183. if name == "project_count" {
  184. _ = json.Unmarshal(bArr, &thisRow.ProjectCount)
  185. quarterData := map[string]interface{}{
  186. "name": fmt.Sprintf("%d-第%d季度", time.Now().Year(), currentQuarter),
  187. "count": thisRow.ProjectCount.DocCount,
  188. }
  189. var redisDataArr []map[string]interface{}
  190. redisData, _ := redis.Get(RedisNameNew, fmt.Sprintf("biddingTrend_%s_%s", industry, area)).([]interface{})
  191. if redisData != nil && len(redisData) > 0 {
  192. redisDataArr = common.ObjArrToMapArr(redisData)
  193. if len(redisDataArr) == 4 {
  194. redisDataArr = append(redisDataArr[1:], quarterData)
  195. redis.Put(RedisNameNew, fmt.Sprintf("biddingTrend_%s_%s", industry, area), redisDataArr, 24*3600*120)
  196. continue
  197. }
  198. }
  199. redisDataArr = append(redisDataArr, quarterData)
  200. redis.Put(RedisNameNew, fmt.Sprintf("biddingTrend_%s_%s", industry, area), redisDataArr, 24*3600*120)
  201. }
  202. }
  203. }
  204. }
  205. }
  206. }
  207. func IndustryInit() {
  208. industryMap = make(map[string][]string)
  209. for _, industry := range config.ServiceArea.Industry {
  210. industryData := public.BaseMysql.SelectBySql(fmt.Sprintf(`SELECT CONCAT(b.name, '_', a.name) as name
  211. FROM global_common_data.code_bidscope a
  212. LEFT JOIN (
  213. SELECT code, name
  214. FROM global_common_data.code_bidscope
  215. WHERE name = '%s'
  216. ) b ON a.pcode = b.code
  217. WHERE b.code IS NOT NULL;`, industry))
  218. var names []string
  219. for _, v := range *industryData {
  220. names = append(names, common.InterfaceToStr(v["name"]))
  221. }
  222. industryMap[industry] = names
  223. }
  224. }
  225. func BiddingTrendInit() {
  226. for _, industry := range config.ServiceArea.Industry {
  227. ds := subzone{
  228. industry: industry,
  229. }
  230. for _, area := range config.ServiceArea.Area {
  231. ds.province = area
  232. ok, err := redis.Exists(RedisNameNew, fmt.Sprintf("biddingTrend_%s_%s", industry, area))
  233. if ok && err == nil {
  234. continue
  235. }
  236. eQuarter := Quarter()
  237. sQuarter := eQuarter.AddDate(-1, 0, 0)
  238. var redisDataArr []map[string]interface{}
  239. for sQuarter.Before(eQuarter) {
  240. currentQuarter := getQuarter(sQuarter.Unix())
  241. res, _, _ := elastic.GetAggs("projectset", "projectset", GetCommonQuerySql(sQuarter.Unix(), sQuarter.AddDate(0, 3, 0).Unix(), area, industry))
  242. if res != nil {
  243. thisRow := marketBuckets{}
  244. for name, object := range res {
  245. bArr, err := object.MarshalJSON()
  246. if len(bArr) == 0 || err != nil {
  247. break
  248. }
  249. if name == "project_count" {
  250. _ = json.Unmarshal(bArr, &thisRow.ProjectCount)
  251. quarterData := map[string]interface{}{
  252. "name": fmt.Sprintf("%d-第%d季度", sQuarter.Year(), currentQuarter),
  253. "count": thisRow.ProjectCount.DocCount,
  254. }
  255. redisDataArr = append(redisDataArr, quarterData)
  256. }
  257. }
  258. }
  259. sQuarter = sQuarter.AddDate(0, 3, 0)
  260. }
  261. redis.Put(RedisNameNew, fmt.Sprintf("biddingTrend_%s_%s", industry, area), redisDataArr, 24*3600*120)
  262. }
  263. }
  264. }
  265. // GetCommonQuerySql 公共筛选
  266. func GetCommonQuerySql(st, et int64, area, industry string) string {
  267. var musts, bools []string
  268. //时间
  269. musts = append(musts, fmt.Sprintf(`{"range":{"jgtime":{"gte":%d,"lte":%d}}}`, st, et))
  270. //地区
  271. if area != "" {
  272. musts = append(musts, fmt.Sprintf(`{"terms":{"area":["%s"]}}`, area))
  273. }
  274. //行业
  275. if len(industryMap[industry]) > 0 {
  276. musts = append(musts, fmt.Sprintf(`{"terms":{"subscopeclass":["%s"]}}`, strings.Join(industryMap[industry], `","`)))
  277. }
  278. //分析报告中标状态限制
  279. musts = append(musts, fmt.Sprintf(query_bool_must, PSearch_DecMust))
  280. aa := fmt.Sprintf(`{"query":{"bool":{"must":[%s],"should":[%s],"minimum_should_match": %d}},"aggs":{"project_count": {"filter": {"match_all":{}}}},"size":0}`, strings.Join(musts, ","), strings.Join(bools, ","), common.If(len(bools) > 0, 1, 0).(int))
  281. fmt.Println(aa)
  282. return fmt.Sprintf(`{"query":{"bool":{"must":[%s],"should":[%s],"minimum_should_match": %d}},"aggs":{"project_count": {"filter": {"match_all":{}}}},"size":0}`, strings.Join(musts, ","), strings.Join(bools, ","), common.If(len(bools) > 0, 1, 0).(int))
  283. }
  284. func Quarter() time.Time {
  285. currentTime := time.Now()
  286. // 获取当前季度
  287. currentQuarter := (currentTime.Month()-1)/3 + 1
  288. // 计算当前季度的开始时间
  289. startMonth := (currentQuarter-1)*3 + 1
  290. quarterStart := time.Date(currentTime.Year(), startMonth, 1, 0, 0, 0, 0, currentTime.Location())
  291. return quarterStart
  292. }
  293. */
  294. // 热门采购数据
  295. func PurchasingData() []map[string]interface{} {
  296. redisData, _ := redis.Get(RedisNameNew, "hotPurchasingData").([]interface{})
  297. if len(redisData) > 0 {
  298. return common.ObjArrToMapArr(redisData)
  299. }
  300. var keyWords []map[string]interface{}
  301. data := public.BaseMysql.SelectBySql("SELECT keyword FROM data_supermarket GROUP BY keyword")
  302. if data != nil && len(*data) > 0 {
  303. for _, m := range *data {
  304. keyWords = append(keyWords, map[string]interface{}{
  305. "keyword": common.InterfaceToStr(m["keyword"]),
  306. "url": fmt.Sprintf("/datasmt/index_1?searchValue=%s", common.InterfaceToStr(m["keyword"])),
  307. })
  308. }
  309. redis.Put(RedisNameNew, "hotPurchasingData", keyWords, RedisTimeout)
  310. }
  311. return keyWords
  312. }