supsearch.go 32 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934
  1. package front
  2. import (
  3. "fmt"
  4. "jy/src/jfw/config"
  5. "jy/src/jfw/jyutil"
  6. "log"
  7. "math/rand"
  8. "strconv"
  9. "strings"
  10. "sync"
  11. "time"
  12. . "app.yhyue.com/moapp/jybase/api"
  13. "app.yhyue.com/moapp/jybase/encrypt"
  14. "app.yhyue.com/moapp/jypkg/common/src/qfw/util/jy"
  15. "app.yhyue.com/moapp/jypkg/jylabutil"
  16. "app.yhyue.com/moapp/jypkg/public"
  17. "app.yhyue.com/moapp/jypkg/common/src/qfw/util/bidsearch"
  18. util "app.yhyue.com/moapp/jybase/common"
  19. "app.yhyue.com/moapp/jybase/redis"
  20. elastic "app.yhyue.com/moapp/jybase/es"
  21. "app.yhyue.com/moapp/jybase/go-xweb/xweb"
  22. "github.com/SKatiyar/qr"
  23. )
  24. type Pcsearch struct {
  25. *xweb.Action
  26. pcSearchIndex xweb.Mapper `xweb:"/jylab/(supsearch|medical|bi)/index.html"` //搜索首页
  27. searchPower xweb.Mapper `xweb:"/jylab/(supsearch|medical|bi)/searchPower"` //搜索权限页面
  28. getNewBids xweb.Mapper `xweb:"/jylab/supsearch/getNewBids"` //最新招标信息
  29. getstatus xweb.Mapper `xweb:"/jylab/supsearch/getstatus"` //实验室开启状态
  30. //proposedProject xweb.Mapper `xweb:"/jylab/supsearch/proposedProject.html"` //拟建项目-- 此功能已取消 影响es 检索功能
  31. qr xweb.Mapper `xweb:"/jylab/supsearch/qr/(.*)"` //生成进入实验室的二维码
  32. changePro xweb.Mapper `xweb:"/jylab/changePro"` //修改提示信息状态
  33. }
  34. var industrylist map[string][]string
  35. var sortArray []string
  36. var PCS_index map[string]interface{}
  37. var PCS_time int
  38. var PCSLock = &sync.Mutex{}
  39. var FileSignBool = false
  40. const (
  41. BidFieldMedical = "0101"
  42. )
  43. var (
  44. // DomainPageType 缓存标签
  45. DomainPageType = map[string]string{
  46. BidFieldMedical: "medical", // 医疗领域
  47. }
  48. )
  49. // MedicalFunctionCode 医疗行业权益代码
  50. const (
  51. MedicalFunctionCode = "lyh_yl_ylbxss"
  52. MobileTagSearchFunctionCode = "zbcgss_zgydbqjs"
  53. )
  54. func init() {
  55. xweb.AddAction(&Pcsearch{})
  56. industrylist, sortArray = jy.Getindustrys(util.ObjToString(config.Sysconfig["industry"]), mongodb)
  57. //清除搜索列表内存缓存 间隔时间
  58. PCS_time = util.IntAll(config.Sysconfig["PCS_time"])
  59. go func() {
  60. time.Sleep(time.Second * 5)
  61. PCS_task()
  62. }()
  63. PCSLock.Lock()
  64. PCS_index = map[string]interface{}{}
  65. PCSLock.Unlock()
  66. //搜索字段添加 附件标识
  67. if FileSignBool, _ = config.Sysconfig["fileSignBool"].(bool); FileSignBool {
  68. bidSearch_field_1 = bidSearch_field_1 + bidSearch_field_file
  69. bidSearch_field = bidSearch_field + bidSearch_field_file
  70. //搜索优化
  71. BidSearchFieldBase += BidSearchFieldFile
  72. BidSearchFieldOfVip += BidSearchFieldFile
  73. }
  74. }
  75. // 定时清理搜索列表页 从redis获取存入内存中的数据
  76. func PCS_task() {
  77. //根据配置延迟 PCS_time 小时执行
  78. sub := time.Hour * time.Duration(PCS_time)
  79. timer := time.NewTimer(sub)
  80. log.Println(PCS_time, "小时后执行清除缓存操作")
  81. defer timer.Stop()
  82. for {
  83. select {
  84. case <-timer.C:
  85. {
  86. PCSLock.Lock()
  87. PCS_index = map[string]interface{}{}
  88. PCSLock.Unlock()
  89. timer.Reset(time.Hour * time.Duration(PCS_time))
  90. }
  91. }
  92. }
  93. }
  94. // 返回内存中列表也的数据,只获取首页,其他页面访问量暂时不多
  95. func PCS_list(page_type string, pageSize int, userId string) []map[string]interface{} {
  96. /*var _page_type = page_type
  97. //如果page_type为空,则是获取非拟建数据。
  98. if page_type == "" {
  99. _page_type = "page_index"
  100. }
  101. PCSLock.Lock()
  102. defer PCSLock.Unlock()
  103. if PCS_index[_page_type] == nil {
  104. PCS_index[_page_type] = Newbids(page_type)[0]
  105. }*/
  106. if pageSize == 0 {
  107. pageSize = 50
  108. }
  109. newbid := Newbids(page_type, userId)
  110. if len(newbid) > 0 {
  111. return newbid[0:pageSize]
  112. } else {
  113. return nil
  114. }
  115. }
  116. func (p *Pcsearch) ChangePro() {
  117. defer util.Catch()
  118. userid := p.GetSession("userId")
  119. if userid != nil {
  120. jylabutil.UpdateAuthory(userid.(string), "i_tablepro", 1)
  121. }
  122. }
  123. // 此功能已失效
  124. func (p *Pcsearch) ProposedProject() error {
  125. defer util.Catch()
  126. var shareid = p.GetString("id")
  127. if len(shareid) == 0 {
  128. shareid = "10"
  129. }
  130. p.T["logid"] = config.Seoconfig["jynjxmy"].(string)
  131. b_word, _, s_word := jy.InterceptSearchKW(p.GetString("keywords"), util.IntAllDef(config.Sysconfig["keywordsLimit"], 35), true)
  132. area := p.GetString("area") //地区
  133. publishtime := p.GetString("publishtime") //发布时间
  134. subtype := p.GetString("subtype") //信息类型
  135. pageSize, _ := p.GetInteger("pageSize") //信息类型
  136. if subtype == "" {
  137. subtype = "拟建"
  138. }
  139. userId, _ := p.GetSession("userId").(string)
  140. var totalPage int64
  141. var list *[]map[string]interface{}
  142. var status = 1
  143. var count int64
  144. if publishtime == "" {
  145. var (
  146. now = time.Now()
  147. startTime = fmt.Sprint(time.Date(now.Year(), now.Month()-6, now.Day(), now.Hour(), now.Minute(), now.Second(), 0, time.Local).Unix()) //最近7天
  148. endTime = fmt.Sprint(now.Unix())
  149. )
  150. publishtime = fmt.Sprintf("%s_%s", startTime, endTime)
  151. }
  152. if len(s_word) > 0 {
  153. status = 2
  154. count, totalPage, list = bidsearch.GetPcBidSearchData(s_word, area, "", publishtime, subtype, "", "", "", "", "", "", "", "", 0, true, nil, bidSearch_field_1, "", false, false, "", pageSize, userId)
  155. listSize := 0
  156. if list != nil {
  157. listSize = len(*list)
  158. }
  159. public.SaveUserSearchLog(p.Request, util.ObjToString(p.GetSession("userId")), count, "pc", "拟建", map[string]interface{}{
  160. "search_word": s_word,
  161. "search_area": area,
  162. "search_publishtime": publishtime,
  163. "pagenum": 1,
  164. "pagesize": listSize,
  165. })
  166. } else {
  167. p.DisableHttpCache()
  168. p.T["list"] = PCS_list("nijian", pageSize, userId) //Newbids("nijian")[0]
  169. totalPage = 10
  170. count = 500
  171. }
  172. if status == 2 {
  173. if list != nil {
  174. for _, v := range *list {
  175. v["_id"] = encrypt.EncodeArticleId2ByCheck(v["_id"].(string))
  176. stp, _ := v["subtype"].(string)
  177. if stp == "" {
  178. stp, _ = v["toptype"].(string)
  179. }
  180. area, _ := v["area"].(string)
  181. v["stypeadd"], v["areaadd"], _ = classify(stp, area, "")
  182. //正文匹配检索关键词
  183. highlight, _ := v["highlight"].(map[string][]string)
  184. detail := ""
  185. for _, val := range highlight["detail"] {
  186. detail += public.ClearHtml.ReplaceAllString(val, "")
  187. }
  188. v["detail"] = detail
  189. }
  190. }
  191. p.T["list"] = list
  192. }
  193. p.T["area"] = area
  194. p.T["subtype"] = subtype
  195. p.T["publishtime"] = publishtime
  196. p.T["timeslot"] = p.GetString("timeslot")
  197. p.T["totalPage"] = totalPage
  198. p.T["count"] = count
  199. p.T["keywords"] = b_word
  200. p.T["searchvalue"] = s_word
  201. p.T["login"] = p.Session().Get("user")
  202. p.SetSession("paramkey", b_word)
  203. if publishtime == "lately-7" {
  204. p.SetSession("parampublishtime", "最近7天")
  205. } else if publishtime == "lately-30" {
  206. p.SetSession("parampublishtime", "最近30天")
  207. } else if publishtime == "thisyear" {
  208. p.SetSession("parampublishtime", "去年")
  209. } else {
  210. p.SetSession("parampublishtime", publishtime)
  211. }
  212. p.SetSession("paramarea", area)
  213. p.T["shareid"] = se.EncodeString(shareid)
  214. return p.Render("/pc/proproject.html", &p.T)
  215. }
  216. func (p *Pcsearch) Getstatus() error {
  217. defer util.Catch()
  218. var supstatus, entstatus, tablepro, dataexportstatus, portraitpower, followent, smartstatus bool
  219. if userid := util.ObjToString(p.GetSession("userId")); userid != "" {
  220. user := jyutil.Compatible.Select(userid,
  221. `{"i_tablepro":1}`)
  222. if len(*user) > 0 {
  223. tablepro = util.Int64All((*user)["i_tablepro"]) == 1
  224. }
  225. }
  226. p.ServeJson(map[string]interface{}{
  227. "smartstatus": smartstatus,
  228. "supstatus": supstatus,
  229. "entstatus": entstatus,
  230. "tablepro": tablepro,
  231. "dataexportstatus": dataexportstatus,
  232. "portraitpower": portraitpower,
  233. "followent": followent,
  234. })
  235. return nil
  236. }
  237. func (p *Pcsearch) GetNewBids() error {
  238. sessVal := p.Session().GetMultiple()
  239. pagenum, _ := p.GetInteger("pageNumber")
  240. pageSize, _ := p.GetInteger("pageSize")
  241. pageType := p.GetString("pageType")
  242. bidField := p.GetString("bid_field")
  243. //userId, _ := p.GetSession("userId").(string)
  244. userId := util.ObjToString(sessVal["base_user_id"])
  245. //baseUserId := p.GetSession("base_user_id")
  246. baseUserId := util.Int64All(sessVal["base_user_id"])
  247. searchGroup, _ := p.GetInteger("searchGroup") //搜索分组;默认0:全部;1:招标采购搜索;2:超前项目。
  248. vipStatus := jy.GetVipState(p.Session(), *config.Middleground, userId)
  249. // 如果是领域化数据j
  250. if bidField != "" {
  251. if domainPageType, ok := DomainPageType[bidField]; ok {
  252. pageType = domainPageType
  253. //bidField = domainPageType
  254. }
  255. //领域化数据 如果没有权限直接返回空数据
  256. if (vipStatus.BigMember <= 0 && vipStatus.VipState <= 0) || (!jy.HasBidFieldPower(config.Middleground, p.Session(), MedicalFunctionCode)) {
  257. p.ServeJson(map[string]interface{}{
  258. "list": []map[string]interface{}{},
  259. "count": 0,
  260. "totalPage": 0,
  261. "total": 0,
  262. })
  263. return nil
  264. }
  265. }
  266. so := &SearchOptimize{
  267. UserId: userId,
  268. PageNum: pagenum,
  269. PageSize: pageSize,
  270. BidField: bidField,
  271. NewUserId: baseUserId,
  272. SearchGroup: searchGroup,
  273. IsPay: vipStatus.IsPayedUser(),
  274. R: p.Request,
  275. }
  276. //搜索条件处理
  277. so.SearchParamsHandle()
  278. var (
  279. list []*map[string]interface{}
  280. count, total int64
  281. )
  282. list, count, total = so.GetBidSearchListByCache()
  283. // count, total, list = so.GetBidSearchList(false)
  284. if pageType == "" { //最新招标信息仅第一页条展示表格多字段
  285. for k, v := range list {
  286. if pagenum == 1 && k < 20 {
  287. continue
  288. }
  289. delete((*v), "bidopentime")
  290. delete((*v), "buyer")
  291. delete((*v), "k")
  292. delete((*v), "projectcode")
  293. delete((*v), "projectname")
  294. delete((*v), "winner")
  295. delete((*v), "timetemp")
  296. delete((*v), "budget")
  297. delete((*v), "s_subscopeclass")
  298. delete((*v), "toptype")
  299. }
  300. }
  301. log.Println("userId:+++", userId)
  302. if userId == "" {
  303. for _, v := range list {
  304. *v = SearchFilter(*v)
  305. }
  306. }
  307. p.ServeJson(map[string]interface{}{
  308. "list": list,
  309. "count": count,
  310. "total": total,
  311. "totalPage": (count + 1) / int64(pageSize),
  312. })
  313. return nil
  314. }
  315. type (
  316. SearchItems struct {
  317. Key string `json:"key" doc:"提交后端接口时需要的Key: keyword"`
  318. Label string `json:"label" doc:"页面展示的标签:关键词"`
  319. Type string `json:"type" doc:"操作类型:下拉、时间选择、多选等"`
  320. DefaultVal []string `json:"defaultVal"`
  321. Options []*SearchItemsValOptions `json:"options" doc:"选项"`
  322. }
  323. SearchItemsValOptions struct {
  324. Key string `json:"key" doc:"后端接受值"`
  325. Label string `json:"label" doc:"展示标签"`
  326. }
  327. )
  328. var (
  329. mobileTagItemsValOptions = []*SearchItemsValOptions{
  330. {Key: "all", Label: "全部"},
  331. {Key: "军队类", Label: "军队类"},
  332. {Key: "武警类", Label: "武警类"},
  333. {Key: "融通类", Label: "融通类"},
  334. {Key: "退役类", Label: "退役类"},
  335. {Key: "融办类", Label: "融办类"},
  336. {Key: "某某类", Label: "“某某”类"},
  337. }
  338. mobileTagItemsValOptionsAll = []string{"军队类", "武警类", "融通类", "退役类", "融办类", "某某类"}
  339. )
  340. // SearchPower 搜索权益列表
  341. func (p *Pcsearch) SearchPower(module string) {
  342. sessVal := p.Session().GetMultiple()
  343. userId := util.ObjToString(sessVal["userId"])
  344. data, err := func() ([]*SearchItems, error) {
  345. var r []*SearchItems
  346. switch module {
  347. case "supsearch":
  348. //搜索页面检索内容
  349. if userId != "" && jy.HasBidFieldPower(config.Middleground, p.Session(), MobileTagSearchFunctionCode) {
  350. r = append(r, &SearchItems{
  351. Key: "mobileTag",
  352. Label: "融创",
  353. Type: "multiple",
  354. DefaultVal: append(mobileTagItemsValOptionsAll, "all"), //默认选择全部
  355. Options: mobileTagItemsValOptions,
  356. })
  357. }
  358. }
  359. return r, nil
  360. }()
  361. p.ServeJson(NewResult(data, err))
  362. }
  363. // PcSearchIndex 路由搜索
  364. func (p *Pcsearch) PcSearchIndex(module string) error {
  365. defer util.Catch()
  366. sessVal := p.Session().GetMultiple()
  367. p.T["logid"] = config.Seoconfig["jysslby"].(string)
  368. pageSize, _ := p.GetInteger("pageSize")
  369. if pageSize == 0 {
  370. pageSize = 50
  371. }
  372. accountId := util.Int64All(sessVal["accountId"])
  373. entAccountId := util.Int64All(sessVal["entAccountId"])
  374. entId := util.Int64All(sessVal["entId"])
  375. entUserId := util.Int64All(sessVal["entUserId"])
  376. keywords := p.GetString("keywords")
  377. industry := strings.TrimSpace(p.GetString("industry")) //选中的行业
  378. area := p.GetString("area") //地区
  379. publishtime := p.GetString("publishtime") //发布时间
  380. timeslot := p.GetString("timeslot") //显示选择时间
  381. toptype := p.GetString("toptype") //信息类型
  382. subtype := p.GetString("subtype") //信息类型
  383. minprice := p.GetString("minprice") //最低价格
  384. maxprice := p.GetString("maxprice") //最高价格
  385. fileExists := p.GetString("fileExists") //是否有附件--所有用户都可用此功能 0:全部;1:有附件;-1:无附件
  386. //搜索优化P260--start--
  387. searchGroup, _ := p.GetInteger("searchGroup") //搜索分组;默认0:全部;1:招标采购搜索;2:超前项目。
  388. searchMode, _ := p.GetInteger("searchMode") //搜索模式;默认0:精准模式(不进行系统分词);1:模糊模式(进行系统分词)。
  389. wordsMode, _ := p.GetInteger("wordsMode") //搜索关键词模式;默认0:包含所有关键词;1:包含任意关键词。
  390. additionalWords := p.GetString("additionalWords") //关键词:附加关键词(副:五组,每组最多15个字符 每组,号隔开)
  391. //--end--
  392. //userId, _ := p.GetSession("userId").(string)
  393. //phone, _ := p.GetSession("phone").(string)
  394. userId := util.ObjToString(sessVal["userId"])
  395. phone := util.ObjToString(sessVal["phone"])
  396. selectType := p.GetString("selectType") //搜索范围
  397. if selectType == "" {
  398. selectType = "title,content"
  399. }
  400. //p353包含采购意向与拟建
  401. noLoginBl := false
  402. if userId == "" {
  403. //未登录用户访问全部信息类型 需要过滤掉 拟建
  404. // p397 未登录用户收回查看拟建权限
  405. if searchGroup < 2 {
  406. if strings.Contains(subtype, "采购意向") || strings.Contains(subtype, "拟建") {
  407. var ss []string
  408. for _, v := range strings.Split(subtype, ",") {
  409. if v != "采购意向" && !strings.Contains(v, "拟建") {
  410. ss = append(ss, v)
  411. }
  412. }
  413. subtype = strings.Join(ss, ",")
  414. }
  415. if subtype == "" {
  416. subtype = "招标预告,招标公告,招标结果,招标信用信息"
  417. noLoginBl = true
  418. }
  419. }
  420. //未登录用户搜索范围 标题和 正文
  421. var selectTypeArr []string
  422. selectTypeSplit := strings.Split(selectType, ",")
  423. // 未登录用户只能搜标题和正文
  424. for i := 0; i < len(selectTypeSplit); i++ {
  425. if selectTypeSplit[i] == "title" || selectTypeSplit[i] == "content" {
  426. selectTypeArr = append(selectTypeArr, selectTypeSplit[i])
  427. }
  428. }
  429. if len(selectTypeArr) > 0 {
  430. selectType = strings.Join(selectTypeArr, ",")
  431. }
  432. if publishtime != "" {
  433. publishtime = ""
  434. }
  435. }
  436. //高级筛选 仅vip用户可查询
  437. var (
  438. hasBuyerTel, hasWinnerTel = "", "" //是否有采购单位电话、是否有中标单位电话 y:有 n:没有
  439. buyerclass = "" //采购单位类别
  440. notkey = "" //排除词
  441. city = "" //城市 付费用户可用
  442. district = ""
  443. regionMap = ""
  444. buyer = ""
  445. winner = ""
  446. agency = ""
  447. mobileTag []string //P513中国移动定制招标采购搜索
  448. )
  449. // 领域化标识
  450. territorialization := p.GetString("bid_field")
  451. switch module {
  452. case "medical": // 领域类型 医疗-0101
  453. if territorialization == "" {
  454. territorialization = "0101"
  455. }
  456. case "BIProperty":
  457. territorialization = territorialization
  458. default:
  459. territorialization = ""
  460. }
  461. if territorialization == "" {
  462. territorialization = p.GetString("property")
  463. }
  464. userInfo := jy.GetVipState(p.Session(), *config.Middleground, userId)
  465. queryItems := userInfo.GetQueryItems(selectType, util.Int64All(config.Sysconfig["bidSearchOldUserLimit"]))
  466. isPayedUser := userInfo.IsPayedUser()
  467. if isPayedUser {
  468. buyerclass = p.GetString("buyerclass")
  469. hasBuyerTel, hasWinnerTel = p.GetString("buyertel"), p.GetString("winnertel")
  470. notkey = p.GetString("notkey")
  471. city = p.GetString("city") //城市 付费用户可用
  472. district = p.GetString("district")
  473. regionMap = p.GetString("regionMap")
  474. //P492招标采购搜索匹配采购单位等优化
  475. buyer = p.GetString("buyer") //采购单位
  476. winner = p.GetString("winner") //中标企业
  477. agency = p.GetString("agency") //招标代理机构
  478. }
  479. //历史导出数据回显
  480. if strings.Contains(p.Url(), "?goback") {
  481. keywords = util.ObjToString(sessVal["Echo_keywords"])
  482. publishtime = util.ObjToString(sessVal["Echo_publishtime"])
  483. area = util.ObjToString(sessVal["Echo_area"])
  484. subtype = util.ObjToString(sessVal["Echo_subtype"])
  485. minprice = util.ObjToString(sessVal["Echo_minprice"])
  486. maxprice = util.ObjToString(sessVal["Echo_maxprice"])
  487. buyerclass = util.ObjToString(sessVal["Echo_buyerclass"])
  488. selectType = util.ObjToString(sessVal["Echo_selectType"])
  489. timeslot = util.ObjToString(sessVal["Echo_timeslot"])
  490. hasBuyerTel = util.ObjToString(sessVal["Echo_hasBuyertel"])
  491. hasWinnerTel = util.ObjToString(sessVal["Echo_hasWinnertel"])
  492. industry = util.ObjToString(sessVal["Echo_industry"])
  493. notkey = util.ObjToString(sessVal["Echo_notkey"])
  494. fileExists = util.ObjToString(sessVal["Echo_fileExists"])
  495. city = util.ObjToString(sessVal["Echo_city"])
  496. district = util.ObjToString(sessVal["Echo_district"])
  497. regionMap = util.ObjToString(sessVal["Echo_regionMap"])
  498. bidField = util.ObjToString(sessVal["Echo_bid_field"]) // 领域化数据 0101-医疗行业
  499. territorialization = util.ObjToString(sessVal["Echo_bid_field"]) // 领域化数据 0101-医疗行业
  500. searchGroup = util.IntAll(sessVal["Echo_searchGroup"]) //搜索分组;默认0:全部;1:招标采购搜索;2:超前项目。
  501. searchMode = util.IntAll(sessVal["Echo_searchMode"]) //搜索模式;默认0:精准模式(不进行系统分词);1:模糊模式(进行系统分词)。
  502. wordsMode = util.IntAll(sessVal["Echo_wordsMode"]) //搜索关键词模式;默认0:包含所有关键词;1:包含任意关键词。
  503. additionalWords = util.ObjToString(sessVal["Echo_additionalWords"]) //关键词:附加关键词(副:五组,每组最多15个字符 每组,号隔开)
  504. queryItems = userInfo.GetQueryItems(selectType, util.Int64All(config.Sysconfig["bidSearchOldUserLimit"]))
  505. //P492招标采购搜索匹配采购单位等优化
  506. buyer = util.ObjToString(sessVal["Echo_buyer"])
  507. winner = util.ObjToString(sessVal["Echo_winner"])
  508. agency = util.ObjToString(sessVal["Echo_agency"])
  509. }
  510. keywordsLimit := util.IntAllDef(config.Sysconfig["keywordsLimit"], 35)
  511. searchLimit := public.IsSearchLimit(queryItems)
  512. //-----------------------------未登录用户支持非单字符查询--------------------------
  513. if userId == "" {
  514. keywordsLimit = util.IntAllDef(config.Sysconfig["keywordsLimitNologin"], 25)
  515. //未登录用户标题、正文都限制,已登录用户只限制正文
  516. searchLimit = true
  517. if len([]rune(keywords)) == 1 {
  518. //未登录用户搜索不让搜索单字
  519. keywords = ""
  520. }
  521. }
  522. var (
  523. list []*map[string]interface{}
  524. count, total int64
  525. secondFlag = ""
  526. isSearch = true
  527. b_word, a_word, s_word, heightKeys = "", "", "", ""
  528. )
  529. onList, _ := jyutil.IsOnTheWhitelist(p.Session())
  530. if keywords != "" {
  531. // p329 非白名单用户 处理通用词
  532. if !onList && len(industry) == 0 {
  533. keywords = jyutil.FilterGeneric(keywords) // 关键词处理通用词
  534. additionalWords = jyutil.AdditionalFilterGeneric(additionalWords) // 附加词处理通用词
  535. }
  536. b_word, a_word, s_word = jy.InterceptSearchKW(keywords, keywordsLimit, len(industry) == 0)
  537. }
  538. if strings.Index(p.Refer(), "/page_workDesktop/work-bench") > -1 {
  539. //超级搜索页面 移动定制搜索标签(仅工作台内展示)
  540. mobileTag = p.GetSlice("mobileTag[]")
  541. //if len(mobileTag) > 0 { //当无该权限,把此字段置空
  542. if !jy.HasBidFieldPower(config.Middleground, p.Session(), MobileTagSearchFunctionCode) {
  543. mobileTag = []string{}
  544. } else if (len(mobileTag) > 0 && mobileTag[0] == "all") || len(mobileTag) == 0 {
  545. mobileTag = mobileTagItemsValOptionsAll
  546. }
  547. //}
  548. }
  549. //医疗领域化信息 用户前提是大会员 超级订阅,才有领域化功能的权限
  550. if territorialization != "" && territorialization != "BIProperty" {
  551. isSearch = false
  552. userInfo := jy.GetVipState(p.Session(), *config.Middleground, userId)
  553. if userInfo.BigMember > 0 || userInfo.VipState > 0 {
  554. if jy.HasBidFieldPower(config.Middleground, p.Session(), MedicalFunctionCode) {
  555. isSearch = true
  556. }
  557. }
  558. }
  559. isLimit := 1
  560. if isSearch {
  561. searchTypeSwitch, _ := config.Sysconfig["searchTypeSwitch"].(bool)
  562. so := NewSearchOptimize(mobileTag, userId, phone, area, city, district, subtype, toptype, publishtime, strings.Join(queryItems, ","), fmt.Sprintf("%s-%s", minprice, maxprice), industry, buyerclass, hasBuyerTel, hasWinnerTel, fileExists, s_word, additionalWords, notkey, "PC", territorialization, "", "", "",
  563. 0, pageSize, searchGroup, searchMode, wordsMode, "", "", 0, 0,
  564. *userInfo, searchTypeSwitch, p.Request, accountId, entAccountId, entId, entUserId, buyer, winner, agency)
  565. heightKeys = so.HeightKeys //主关键词和附加词合并,多组空格隔开,作为前端渲染高亮关键词使用
  566. //关键词 行业 附加词
  567. //放开用户不输入关键词可搜索 --P297需求
  568. // p329 反爬白名单用户放开 非反爬白名单用户不放开未输入关键词
  569. if len(s_word) > 0 || (len(s_word) == 0 && onList) || len(industry) > 0 || strings.TrimSpace(so.AdditionalWords) != "" || len(so.MobileTag) > 0 {
  570. if searchLimit {
  571. isLimit = public.Lst.IsLimited(p.Request, p.ResponseWriter, p.Session(), isPayedUser)
  572. if isLimit == 1 { //没有被限制
  573. defer public.Lst.Limit()
  574. }
  575. }
  576. if isLimit == 1 {
  577. count, total, list = so.GetBidSearchList(false)
  578. }
  579. } else {
  580. p.DisableHttpCache()
  581. list, count, total = so.GetBidSearchListByCache()
  582. }
  583. }
  584. if noLoginBl {
  585. subtype = ""
  586. }
  587. if userId == "" {
  588. for _, v := range list {
  589. *v = SearchFilter(*v)
  590. }
  591. }
  592. p.T["list"] = list
  593. p.T["secondFlag"] = secondFlag
  594. p.T["area"] = area
  595. p.T["publishtime"] = publishtime
  596. p.T["timeslot"] = timeslot
  597. p.T["toptype"] = toptype
  598. p.T["subtype"] = subtype
  599. p.T["searchvalue"] = keywords //搜索关键词
  600. p.T["minprice"] = minprice
  601. p.T["maxprice"] = maxprice
  602. p.T["buyerclass"] = buyerclass
  603. p.T["buyertel"] = hasBuyerTel
  604. p.T["winnertel"] = hasWinnerTel
  605. p.T["notkey"] = notkey
  606. p.T["fileExists"] = fileExists
  607. p.T["city"] = city
  608. p.T["district"] = district
  609. p.T["regionMap"] = regionMap
  610. p.T["bid_field"] = territorialization
  611. p.SetSession("paramkey", b_word)
  612. switch publishtime {
  613. case "lately-7":
  614. p.SetSession("parampublishtime", "最近7天")
  615. case "lately-30":
  616. p.SetSession("parampublishtime", "最近30天")
  617. case "thisyear":
  618. p.SetSession("parampublishtime", "近一年")
  619. case "threeyear":
  620. p.SetSession("parampublishtime", "近三年")
  621. case "fiveyear":
  622. p.SetSession("parampublishtime", "近五年")
  623. default:
  624. p.SetSession("parampublishtime", publishtime)
  625. }
  626. p.SetSession("paramarea", area)
  627. if subtype != "" {
  628. p.SetSession("paraminfotype", subtype)
  629. } else {
  630. p.SetSession("paraminfotype", toptype)
  631. }
  632. //}
  633. p.T["selectType"] = selectType
  634. p.T["login"] = p.Session().Get("user")
  635. p.T["count"] = count
  636. p.T["totalPage"] = (count + 1) / int64(pageSize)
  637. p.T["keywords"] = keywords //搜索关键词
  638. p.T["heightWords"] = heightKeys //主关键词和附加词合并后
  639. p.T["industry"] = industry
  640. p.T["industrylist"] = industrylist
  641. p.T["sortArray"] = sortArray
  642. p.T["showVipScreen"] = isPayedUser
  643. p.T["bidField"] = territorialization
  644. p.T["module"] = module
  645. p.T["interceptKeyWords"] = b_word //超出限制关键词限制长度 截取后
  646. p.T["interceptOtherWords"] = a_word //超出限制关键词限制长度 截取后 提示关键词
  647. p.T["interceptLimit"] = keywordsLimit
  648. //
  649. p.T["searchGroup"] = searchGroup
  650. p.T["searchMode"] = searchMode
  651. p.T["wordsMode"] = wordsMode
  652. p.T["additionalWords"] = additionalWords
  653. p.T["total"] = total
  654. p.T["isVip"] = userInfo.VipState > 0
  655. p.T["isMember"] = userInfo.BigMember > 0
  656. p.T["isEntniche"] = userInfo.EntMember > 0
  657. p.T["isEntnicheNew"] = userInfo.IsNewEnt
  658. p.T["isEntService"] = userInfo.EntService
  659. p.T["vipBefore202209"] = userInfo.VipState > 0 && userInfo.VipStartData < util.Int64All(config.Sysconfig["contextOldVipLimit"]) //超级订阅 超强项目
  660. //
  661. cooperateCode := ""
  662. if userId != "" {
  663. //企业画像 权限
  664. p.T["portraitpower"] = jylabutil.IsAuthorized(userId, "i_portraitpower")
  665. } else {
  666. if cc, err := p.GetCookie(jy.ChannelCookieName); err == nil {
  667. cooperateCode = cc.Value
  668. }
  669. }
  670. p.T["cooperateCode"] = cooperateCode
  671. p.T["isLimit"] = isLimit
  672. if module == "supsearch" {
  673. p.T["simpleTemplateData"] = map[string]interface{}{
  674. "isEntniche": p.T["isEntniche"],
  675. "isVip": p.T["isVip"],
  676. "isMember": p.T["isMember"],
  677. "vipBefore202209": p.T["vipBefore202209"],
  678. "searchMode": searchMode,
  679. "searchvalue": keywords,
  680. "additionalWords": additionalWords,
  681. "listLength": util.If(list != nil, len(list), 0),
  682. }
  683. }
  684. return p.Render("/pc/supsearch.html", &p.T)
  685. }
  686. // Newbids 最新招标信息 --已失效
  687. func Newbids(p, userId string) []map[string]interface{} {
  688. return nil
  689. ////fmt.Println("11111", redis.Get("newother", "index_list"))
  690. //nologin := ""
  691. //count := 500
  692. //pagenum := 10
  693. //limit := 50
  694. //if userId == "" {
  695. // nologin = "_nologin"
  696. // count = bidsearch.SearchMaxPageCount_NOLOGIN
  697. // pagenum = 20
  698. // limit = 250
  699. //}
  700. //indexOk, _ := redis.Exists("newother", "index_list"+p+nologin)
  701. //pages := []map[string]interface{}{}
  702. //if indexOk {
  703. // pages = util.ObjArrToMapArr(redis.Get("newother", "index_list"+p+nologin).([]interface{}))
  704. //}
  705. //if len(pages) == 0 {
  706. // var list *[]map[string]interface{}
  707. // subtype := ""
  708. // bidField := ""
  709. // // 判断是不是医疗行业
  710. // if p == "medical" {
  711. // bidField = "0101"
  712. // } else {
  713. // if len(p) > 0 {
  714. // subtype = "拟建"
  715. // }
  716. // //未登录用户访问全部信息类型 需要过滤掉 拟建和采购意向
  717. // if subtype == "" {
  718. // subtype = "拟建,招标预告,招标公告,招标结果,招标信用信息"
  719. // }
  720. // }
  721. // //查询置顶信息
  722. // var ss []map[string]interface{}
  723. // ls := top500(subtype, bidField, userId)
  724. // if ls != nil && len(*ls) > 0 {
  725. // ss = append(ss, *ls...)
  726. // }
  727. // //pages = append(pages, ls)
  728. // if ls == nil || len(*ls) < count {
  729. // intns := make([]int, 0)
  730. // for i := 0; i < pagenum; i++ {
  731. // if len(intns) == 0 {
  732. // intns = append(intns, rand.Intn(1000))
  733. // } else {
  734. // for {
  735. // v := rand.Intn(intns[(i-1)] + 1000)
  736. // if v-intns[(i-1)] > limit {
  737. // intns = append(intns, v)
  738. // break
  739. // }
  740. // }
  741. // }
  742. // }
  743. // for i := 0; i < pagenum; i++ {
  744. // _, list = getLastNewsData("", "", "", "", subtype, "", "", "", "", "", "", "", "Y", intns[i], true, false, "", bidField, limit)
  745. // if list != nil && len(*list) > 0 {
  746. // ss = append(ss, *list...)
  747. // }
  748. // }
  749. // }
  750. // data := duplicateRemoval(ss)
  751. // if len(data) > 0 {
  752. // pages = data
  753. // redis.Put("newother", "index_list"+p+nologin, pages, 60*60*24)
  754. // pages = util.ObjArrToMapArr(redis.Get("newother", "index_list"+p+nologin).([]interface{}))
  755. // }
  756. //}
  757. //return pages
  758. }
  759. // Newbids 最新招标信息
  760. func NewBidddingsForSEO(p string, pageNum, limit int) []map[string]interface{} {
  761. indexOk, _ := redis.Exists("newother", "index_list_"+p)
  762. pages := []map[string]interface{}{}
  763. if indexOk {
  764. pages = util.ObjArrToMapArr(redis.Get("newother", "index_list_"+p).([]interface{}))
  765. } else {
  766. var ss []map[string]interface{}
  767. intns := make([]int, 0)
  768. for i := 0; i < pageNum; i++ {
  769. if len(intns) == 0 {
  770. intns = append(intns, rand.Intn(30))
  771. } else {
  772. for {
  773. v := rand.Intn(intns[(i-1)] + 50)
  774. if v-intns[(i-1)] > limit {
  775. intns = append(intns, v)
  776. break
  777. }
  778. }
  779. }
  780. }
  781. for i := 0; i < pageNum; i++ {
  782. list := elastic.GetPage(INDEX, TYPE, "", `{"publishtime":-1}`, bidField, intns[i], limit)
  783. if list != nil && len(*list) > 0 {
  784. ss = append(ss, *list...)
  785. }
  786. }
  787. if len(ss) > 0 {
  788. pages = ss
  789. redis.Put("newother", "index_list_"+p, ss, 60*60*24)
  790. }
  791. }
  792. return pages
  793. }
  794. func duplicateRemoval(ss []map[string]interface{}) []map[string]interface{} {
  795. d := make(map[string]interface{})
  796. data := []map[string]interface{}{}
  797. for _, v := range ss {
  798. id := util.InterfaceToStr(v["_id"])
  799. if _, ok := d[id]; ok || id == "" {
  800. continue
  801. }
  802. t := time.Unix(util.Int64All(v["publishtime"]), 0)
  803. v["timetemp"] = fmt.Sprint(util.Int64All(v["publishtime"]))
  804. v["_id"] = encrypt.EncodeArticleId2ByCheck(id)
  805. v["time"] = util.TimeDiff(t)
  806. var stp = ""
  807. if v["subtype"] != nil {
  808. stp, _ = v["subtype"].(string)
  809. } else {
  810. stp = ""
  811. }
  812. if stp == "" && v["toptype"] != nil {
  813. stp, _ = v["toptype"].(string)
  814. }
  815. area, _ := v["area"].(string)
  816. indtry := util.ObjToString(v["industry"])
  817. v["stypeadd"], v["areaadd"], v["indadd"] = classify(stp, area, indtry)
  818. if v["filetext"] != nil {
  819. delete(v, "filetext")
  820. v["fileExists"] = true
  821. }
  822. if _, ok := d[id]; ok {
  823. continue
  824. }
  825. d[id] = true
  826. v["k"] = util.IntAll(v["k"]) + 1
  827. data = append(data, v)
  828. }
  829. return data
  830. }
  831. var topTypeMap = map[string]string{
  832. "招标预告": "预告",
  833. "招标公告": "招标",
  834. "招标结果": "结果",
  835. "招标信用信息": "其它",
  836. }
  837. // 未登录变成top5000了...
  838. func top500(subtype string, bidField string, userId string) (list *[]map[string]interface{}) {
  839. qstr := ""
  840. if bidField != "" {
  841. // 如果是领域化数据
  842. q := `{"query": {"bool": {"should": [{"term": {"dataweight": 1}}], "must": [
  843. {"term": {"bid_field": "%s"}}]}}}`
  844. qstr = fmt.Sprintf(q, bidField)
  845. } else {
  846. var query = ``
  847. qstr = `{"query": {"bool": {"must": [%s]}}}`
  848. if subtype != "" {
  849. var topTypes []string
  850. var subTypes []string
  851. for _, v := range strings.Split(subtype, ",") {
  852. if v1, ok := topTypeMap[v]; ok {
  853. topTypes = append(topTypes, fmt.Sprintf(`"%s"`, v1))
  854. } else {
  855. subTypes = append(subTypes, fmt.Sprintf(`"%s"`, v))
  856. }
  857. }
  858. log.Println("信息类型搜索:", topTypes, subTypes)
  859. if len(subTypes) > 0 && len(topTypes) > 0 {
  860. query = fmt.Sprintf(`{"bool": {"should": [{"terms": {"subtype": [%s]}},{"terms": {"toptype": [%s]}}]}}`, strings.Join(subTypes, ","), strings.Join(topTypes, ","))
  861. } else if len(subTypes) > 0 {
  862. query += fmt.Sprintf(`{"terms":{"subtype":[%s]}}`, strings.Join(subTypes, ","))
  863. } else if len(topTypes) > 0 {
  864. query += fmt.Sprintf(`{"terms":{"toptype":[%s]}}`, strings.Join(topTypes, ","))
  865. }
  866. }
  867. if query != `` {
  868. query = query + `,` + `{"term": {"dataweight": 1}}`
  869. } else {
  870. query = `{"term": {"dataweight": 1}}`
  871. }
  872. qstr = fmt.Sprintf(qstr, query)
  873. }
  874. count := 500
  875. if userId == "" {
  876. count = bidsearch.SearchMaxPageCount_NOLOGIN
  877. }
  878. repl := elastic.GetAllByNgram(INDEX, TYPE, qstr, `"title"`, `{"publishtime":-1}`, bidSearch_field, 0, count, 115, false)
  879. if repl != nil && *repl != nil && len(*repl) > 0 {
  880. public.BidListConvert("", repl)
  881. list = repl
  882. }
  883. return
  884. }
  885. // 二维码图片
  886. func (p *Pcsearch) Qr(t string) error {
  887. openid := p.GetSession("openid")
  888. if openid == nil {
  889. return nil
  890. }
  891. w := p.ResponseWriter
  892. w.Header().Set("Cache-Control", "no-cache, no-store, must-revalidate")
  893. w.Header().Set("Pragma", "no-cache")
  894. w.Header().Set("Expires", "0")
  895. w.Header().Set("Content-Type", "image/png")
  896. data := config.Sysconfig["webdomain"].(string) + "/front/sess/" + sewx.EncodeString(openid.(string)+",uid,"+strconv.Itoa(int(time.Now().Unix()))+",qrToLab") + "__" + t
  897. r, _ := qr.Encode(data, qr.M)
  898. pngdat := r.PNG()
  899. _, err := w.Write(pngdat)
  900. return err
  901. }