|
@@ -0,0 +1,428 @@
|
|
|
|
+package main
|
|
|
|
+
|
|
|
|
+import (
|
|
|
|
+ . "app.yhyue.com/moapp/jybase/common"
|
|
|
|
+ . "app.yhyue.com/moapp/jybase/mongodb"
|
|
|
|
+ "context"
|
|
|
|
+ "flag"
|
|
|
|
+ "fmt"
|
|
|
|
+ "github.com/gogf/gf/v2/container/garray"
|
|
|
|
+ "github.com/gogf/gf/v2/container/gmap"
|
|
|
|
+ "github.com/gogf/gf/v2/container/gset"
|
|
|
|
+ "github.com/gogf/gf/v2/frame/g"
|
|
|
|
+ "github.com/gogf/gf/v2/os/gctx"
|
|
|
|
+ "github.com/gogf/gf/v2/os/gtime"
|
|
|
|
+ "github.com/gogf/gf/v2/text/gstr"
|
|
|
|
+ "github.com/gogf/gf/v2/util/gconv"
|
|
|
|
+ "golang.org/x/net/html"
|
|
|
|
+ "net/rpc"
|
|
|
|
+ "regexp"
|
|
|
|
+ "strings"
|
|
|
|
+ "sync"
|
|
|
|
+ "time"
|
|
|
|
+)
|
|
|
|
+
|
|
|
|
+var (
|
|
|
|
+ TaskConfig *taskConfig
|
|
|
|
+ mgo *MongodbSim
|
|
|
|
+ mgoBid *MongodbSim
|
|
|
|
+)
|
|
|
|
+
|
|
|
|
+type taskConfig struct {
|
|
|
|
+ LastTime int64
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+type BidDataItem struct {
|
|
|
|
+ Zbgs *BidDataObj //中标公示
|
|
|
|
+ Zcgs *BidDataObj //招采公示
|
|
|
|
+ Yxsjgs *BidDataObj //意向商机公示
|
|
|
|
+
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+type BidDataObj struct {
|
|
|
|
+ Winners *gset.Set
|
|
|
|
+ Purchasinglist *gset.Set
|
|
|
|
+ BidDataDetails *garray.SortedArray
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+type BidDataDetail struct {
|
|
|
|
+ ProjectName string //项目名称
|
|
|
|
+ ProjectCode string //项目编号
|
|
|
|
+ Area string //项目地区
|
|
|
|
+ Buyer string //招采单位
|
|
|
|
+ Budget string //预算金额
|
|
|
|
+ Amount float64 //金额
|
|
|
|
+ Winner string //中标单位
|
|
|
|
+ Bidamount string //中标金额
|
|
|
|
+ Detail string //建设内容
|
|
|
|
+ Bidendtime string //投标截止时间
|
|
|
|
+ PurchaseTime string //预计采购时间
|
|
|
|
+ Projectscope string //需求概况 projectscope
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+type Article struct {
|
|
|
|
+ Title string
|
|
|
|
+ Content string
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+func newBidDataObj() *BidDataObj {
|
|
|
|
+ return &BidDataObj{Winners: gset.New(true), Purchasinglist: gset.New(true), BidDataDetails: garray.NewSortedArray(func(a, b interface{}) int {
|
|
|
|
+ if a.(*BidDataDetail).Amount > b.(*BidDataDetail).Amount {
|
|
|
|
+ return -1
|
|
|
|
+ } else if a.(*BidDataDetail).Amount < b.(*BidDataDetail).Amount {
|
|
|
|
+ return 1
|
|
|
|
+ }
|
|
|
|
+ return 0
|
|
|
|
+ }, true)}
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+func init() {
|
|
|
|
+ ctx := gctx.New()
|
|
|
|
+ mgo = &MongodbSim{
|
|
|
|
+ MongodbAddr: g.Config().MustGet(ctx, "mongodb.main.address").String(),
|
|
|
|
+ Size: g.Config().MustGet(ctx, "mongodb.main.size").Int(),
|
|
|
|
+ DbName: g.Config().MustGet(ctx, "mongodb.main.dbName").String(),
|
|
|
|
+ UserName: g.Config().MustGet(ctx, "mongodb.main.userName").String(),
|
|
|
|
+ Password: g.Config().MustGet(ctx, "mongodb.main.password").String(),
|
|
|
|
+ }
|
|
|
|
+ mgo.InitPool()
|
|
|
|
+ mgoBid = &MongodbSim{
|
|
|
|
+ MongodbAddr: g.Config().MustGet(ctx, "mongodb.bidding.address").String(),
|
|
|
|
+ Size: g.Config().MustGet(ctx, "mongodb.bidding.size").Int(),
|
|
|
|
+ DbName: g.Config().MustGet(ctx, "mongodb.bidding.dbName").String(),
|
|
|
|
+ UserName: g.Config().MustGet(ctx, "mongodb.bidding.userName").String(),
|
|
|
|
+ Password: g.Config().MustGet(ctx, "mongodb.bidding.password").String(),
|
|
|
|
+ }
|
|
|
|
+ mgoBid.InitPool()
|
|
|
|
+ ReadConfig("./task.json", &TaskConfig)
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+func main() {
|
|
|
|
+ model := flag.Int("m", 0, "1:上传素材 2:非定时任务")
|
|
|
|
+ startTime := flag.Int64("s", 0, "开始时间")
|
|
|
|
+ endTime := flag.Int64("e", 0, "结束时间")
|
|
|
|
+ flag.Parse()
|
|
|
|
+ //addDraft(0, 1736289976) //f_sourceinfo_2025Jslt_msx
|
|
|
|
+ //addDraft(1740731400, 1840731400) //f_sourceinfo_2025Sjcs 江苏 西藏
|
|
|
|
+ //return
|
|
|
|
+ if *model == 1 {
|
|
|
|
+ addMaterial()
|
|
|
|
+ } else if *model == 2 {
|
|
|
|
+ addDraft(*startTime, *endTime)
|
|
|
|
+ } else {
|
|
|
|
+ SimpleCrontab(true, g.Config().MustGet(gctx.New(), "timeTask").String(), func() {
|
|
|
|
+ et := time.Now().Unix()
|
|
|
|
+ addDraft(TaskConfig.LastTime, et)
|
|
|
|
+ TaskConfig.LastTime = et
|
|
|
|
+ WriteSysConfig("./task.json", *TaskConfig)
|
|
|
|
+ })
|
|
|
|
+ <-chan bool(nil)
|
|
|
|
+ }
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+func addMaterial() {
|
|
|
|
+ ctx := gctx.New()
|
|
|
|
+ var path = "./thumb.png"
|
|
|
|
+ result, err := g.Client().Post(ctx, "https://api.weixin.qq.com/cgi-bin/material/add_material?access_token="+getAccessToken(ctx)+"&type=image", "media=@file:"+path)
|
|
|
|
+ if err != nil {
|
|
|
|
+ g.Log().Error(ctx, err)
|
|
|
|
+ return
|
|
|
|
+ }
|
|
|
|
+ defer result.Close()
|
|
|
|
+ g.Log().Info(ctx, "新增永久素材请求返回结果", result.ReadAllString())
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+// 新增草稿箱
|
|
|
|
+func addDraft(startTime, endTime int64) {
|
|
|
|
+ ctx := gctx.New()
|
|
|
|
+ g.Log().Info(ctx, "开始新增草稿箱任务。。。")
|
|
|
|
+ sess := mgo.GetMgoConn()
|
|
|
|
+ defer mgo.DestoryMongoConn(sess)
|
|
|
|
+ it := sess.DB(g.Config().MustGet(ctx, "mongodb.main.dbName").String()).C(g.Config().MustGet(ctx, "mongodb.main.collection").String()).Find(map[string]interface{}{
|
|
|
|
+ "i_updatetime": map[string]interface{}{
|
|
|
|
+ "$gte": startTime,
|
|
|
|
+ "$lt": endTime,
|
|
|
|
+ },
|
|
|
|
+ }).Select(map[string]interface{}{"id": 1, "v_baseinfo": 1}).Iter()
|
|
|
|
+ all := gmap.New(true)
|
|
|
|
+ pool := make(chan bool, 5)
|
|
|
|
+ wait := &sync.WaitGroup{}
|
|
|
|
+ index := 0
|
|
|
|
+ areas := map[string]bool{}
|
|
|
|
+ for _, v := range g.Config().MustGet(ctx, "areas").Strings() {
|
|
|
|
+ areas[v] = true
|
|
|
|
+ }
|
|
|
|
+ for mt := make(map[string]interface{}); it.Next(&mt); {
|
|
|
|
+ pool <- true
|
|
|
|
+ wait.Add(1)
|
|
|
|
+ go func(mn map[string]interface{}) {
|
|
|
|
+ defer func() {
|
|
|
|
+ <-pool
|
|
|
|
+ wait.Done()
|
|
|
|
+ }()
|
|
|
|
+ v_baseinfo, _ := mn["v_baseinfo"].(map[string]interface{})
|
|
|
|
+ area, _ := v_baseinfo["area"].(string)
|
|
|
|
+ toptype, _ := v_baseinfo["toptype"].(string)
|
|
|
|
+ subtype, _ := v_baseinfo["subtype"].(string)
|
|
|
|
+ if !areas[area] || (toptype != "招标" && toptype != "采购意向" && subtype != "中标" && subtype != "成交") {
|
|
|
|
+ return
|
|
|
|
+ }
|
|
|
|
+ var bdi *BidDataItem
|
|
|
|
+ if all.Get(area) == nil {
|
|
|
|
+ bdi = &BidDataItem{Zbgs: newBidDataObj(), Zcgs: newBidDataObj(), Yxsjgs: newBidDataObj()}
|
|
|
|
+ all.Set(area, bdi)
|
|
|
|
+ } else {
|
|
|
|
+ bdi = all.Get(area).(*BidDataItem)
|
|
|
|
+ }
|
|
|
|
+ var bdo *BidDataObj
|
|
|
|
+ if toptype == "招标" {
|
|
|
|
+ bdo = bdi.Zcgs
|
|
|
|
+ } else if toptype == "结果" {
|
|
|
|
+ bdo = bdi.Zbgs
|
|
|
|
+ } else {
|
|
|
|
+ bdo = bdi.Yxsjgs
|
|
|
|
+ }
|
|
|
|
+ purchasinglist, _ := v_baseinfo["purchasinglist"].([]interface{})
|
|
|
|
+ bidendtime := gconv.Int64(v_baseinfo["bidendtime"])
|
|
|
|
+ procurementlist, _ := v_baseinfo["procurementlist"].([]interface{})
|
|
|
|
+ if id := gconv.String(mn["id"]); id != "" && (purchasinglist == nil || len(purchasinglist) == 0 || v_baseinfo["bidendtime"] == nil || procurementlist == nil || len(procurementlist) == 0) {
|
|
|
|
+ bidding, ok := mgoBid.FindById("bidding", id, `{"purchasinglist":1,"bidendtime":1,"procurementlist":1}`)
|
|
|
|
+ if ok && bidding != nil && len(*bidding) > 0 {
|
|
|
|
+ if purchasinglist == nil {
|
|
|
|
+ purchasinglist, _ = (*bidding)["purchasinglist"].([]interface{})
|
|
|
|
+ }
|
|
|
|
+ if bidendtime == 0 {
|
|
|
|
+ bidendtime = gconv.Int64((*bidding)["bidendtime"])
|
|
|
|
+ }
|
|
|
|
+ if procurementlist == nil {
|
|
|
|
+ procurementlist, _ = (*bidding)["procurementlist"].([]interface{})
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ //
|
|
|
|
+ if len(purchasinglist) > 0 {
|
|
|
|
+ firstOne, _ := purchasinglist[0].(map[string]interface{})
|
|
|
|
+ itemname := gconv.String(firstOne["itemname"])
|
|
|
|
+ if itemname != "" {
|
|
|
|
+ bdo.Purchasinglist.Add(itemname)
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ //
|
|
|
|
+ purchaseTime := ""
|
|
|
|
+ if len(procurementlist) > 0 {
|
|
|
|
+ firstOne, _ := procurementlist[0].(map[string]interface{})
|
|
|
|
+ purchaseTime = gconv.String(firstOne["expurasingtime"])
|
|
|
|
+ }
|
|
|
|
+ //
|
|
|
|
+ winner, _ := v_baseinfo["winner"].(string)
|
|
|
|
+ bdo.Winners.Add(winner)
|
|
|
|
+ //
|
|
|
|
+ detail := filterHtml(gconv.String(v_baseinfo["detail"]))
|
|
|
|
+ newDetail := gstr.SubStrRune(detail, 0, 300)
|
|
|
|
+ if detail != newDetail {
|
|
|
|
+ newDetail += g.Config().MustGet(ctx, "template.captureAppend").String()
|
|
|
|
+ }
|
|
|
|
+ bdd := &BidDataDetail{
|
|
|
|
+ ProjectName: gconv.String(v_baseinfo["projectname"]),
|
|
|
|
+ ProjectCode: gconv.String(v_baseinfo["projectcode"]),
|
|
|
|
+ Area: area,
|
|
|
|
+ Buyer: gconv.String(v_baseinfo["buyer"]),
|
|
|
|
+ Budget: gconv.String(v_baseinfo["budget"]),
|
|
|
|
+ Winner: winner,
|
|
|
|
+ Bidamount: gconv.String(v_baseinfo["bidamount"]),
|
|
|
|
+ Detail: newDetail,
|
|
|
|
+ PurchaseTime: purchaseTime,
|
|
|
|
+ Projectscope: gconv.String(v_baseinfo["projectscope"]),
|
|
|
|
+ }
|
|
|
|
+ if v_baseinfo["bidamount"] != nil {
|
|
|
|
+ bdd.Amount = gconv.Float64(bdd.Bidamount)
|
|
|
|
+ } else {
|
|
|
|
+ bdd.Amount = gconv.Float64(bdd.Budget)
|
|
|
|
+ }
|
|
|
|
+ if bdd.ProjectName == "" {
|
|
|
|
+ bdd.ProjectName = gconv.String(v_baseinfo["title"])
|
|
|
|
+ }
|
|
|
|
+ if bidendtime > 0 {
|
|
|
|
+ bdd.Bidendtime = gtime.New(bidendtime).Layout(time.DateTime)
|
|
|
|
+ }
|
|
|
|
+ bdo.BidDataDetails.Add(bdd)
|
|
|
|
+ }(mt)
|
|
|
|
+ index++
|
|
|
|
+ if index%500 == 0 {
|
|
|
|
+ g.Log().Info(ctx, "加载清洗数据。。。", index)
|
|
|
|
+ }
|
|
|
|
+ mt = make(map[string]interface{})
|
|
|
|
+ }
|
|
|
|
+ wait.Wait()
|
|
|
|
+ g.Log().Info(ctx, "清洗数据加载结束。。。", index)
|
|
|
|
+ articles := []*Article{}
|
|
|
|
+ ymd := gtime.Now().Format("Ymd")
|
|
|
|
+ purchasingSize := g.Config().MustGet(ctx, "template.purchasingSize").Int()
|
|
|
|
+ winnerSize := g.Config().MustGet(ctx, "template.winnerSize").Int()
|
|
|
|
+ all.Iterator(func(k, v interface{}) bool {
|
|
|
|
+ kk := k.(string)
|
|
|
|
+ vv := v.(*BidDataItem)
|
|
|
|
+ //
|
|
|
|
+ if !vv.Zbgs.BidDataDetails.IsEmpty() {
|
|
|
|
+ vv.Zbgs.BidDataDetails.Sort()
|
|
|
|
+ content := fmt.Sprintf(g.Config().MustGet(ctx, "template.zbgs.content").String(), kk, garray.NewArrayFrom(vv.Zbgs.Purchasinglist.Pops(purchasingSize)).Join("、"), garray.NewArrayFrom(vv.Zbgs.Winners.Pops(winnerSize)).Join("、"))
|
|
|
|
+ for k, v := range vv.Zbgs.BidDataDetails.PopLefts(g.Config().MustGet(ctx, "template.zhongProjectSize").Int()) {
|
|
|
|
+ vv := v.(*BidDataDetail)
|
|
|
|
+ content += fmt.Sprintf("<br>项目%s:%s", NumToChinese(k+1), vv.ProjectName)
|
|
|
|
+ if vv.Buyer != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>招采单位:%s", vv.Buyer)
|
|
|
|
+ }
|
|
|
|
+ if vv.Winner != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>中标单位:%s", vv.Winner)
|
|
|
|
+ }
|
|
|
|
+ if vv.Bidamount != "" && vv.Bidamount != "0" {
|
|
|
|
+ content += fmt.Sprintf("<br>中标金额:%s", vv.Bidamount)
|
|
|
|
+ }
|
|
|
|
+ if vv.Detail != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>建设内容:%s", vv.Detail)
|
|
|
|
+ }
|
|
|
|
+ content += "<br>"
|
|
|
|
+ }
|
|
|
|
+ articles = append(articles, &Article{
|
|
|
|
+ Title: fmt.Sprintf("%s_%s_中标标讯", ymd, kk),
|
|
|
|
+ Content: content,
|
|
|
|
+ })
|
|
|
|
+ }
|
|
|
|
+ //
|
|
|
|
+ if !vv.Zcgs.BidDataDetails.IsEmpty() {
|
|
|
|
+ vv.Zcgs.BidDataDetails.Sort()
|
|
|
|
+ content := ""
|
|
|
|
+ var allBudget float64
|
|
|
|
+ for k, v := range vv.Zcgs.BidDataDetails.PopLefts(g.Config().MustGet(ctx, "template.zhaoProjectSize").Int()) {
|
|
|
|
+ vv := v.(*BidDataDetail)
|
|
|
|
+ allBudget += gconv.Float64(vv.Budget)
|
|
|
|
+ content += fmt.Sprintf("<br>项目%s:%s", NumToChinese(k+1), vv.ProjectName)
|
|
|
|
+ if vv.ProjectCode != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>项目编号:%s", vv.ProjectCode)
|
|
|
|
+ }
|
|
|
|
+ if vv.Buyer != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>采购单位:%s", vv.Buyer)
|
|
|
|
+ }
|
|
|
|
+ if vv.Area != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>项目地区:%s", vv.Area)
|
|
|
|
+ }
|
|
|
|
+ if vv.Budget != "" && vv.Budget != "0" {
|
|
|
|
+ content += fmt.Sprintf("<br>预算金额:%s", vv.Budget)
|
|
|
|
+ }
|
|
|
|
+ if vv.Bidendtime != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>投标截止时间:%s", vv.Bidendtime)
|
|
|
|
+ }
|
|
|
|
+ if vv.Detail != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>项目建设内容:%s", vv.Detail)
|
|
|
|
+ }
|
|
|
|
+ content += "<br>"
|
|
|
|
+ }
|
|
|
|
+ content = fmt.Sprintf(g.Config().MustGet(ctx, "template.zcgs.content").String(), kk, garray.NewArrayFrom(vv.Zcgs.Purchasinglist.Pops(purchasingSize)).Join("、"), allBudget) + content
|
|
|
|
+ articles = append(articles, &Article{
|
|
|
|
+ Title: fmt.Sprintf("%s_%s_招标标讯", ymd, kk),
|
|
|
|
+ Content: content,
|
|
|
|
+ })
|
|
|
|
+ }
|
|
|
|
+ //
|
|
|
|
+ if !vv.Yxsjgs.BidDataDetails.IsEmpty() {
|
|
|
|
+ vv.Yxsjgs.BidDataDetails.Sort()
|
|
|
|
+ content := ""
|
|
|
|
+ for k, v := range vv.Yxsjgs.BidDataDetails.PopLefts(g.Config().MustGet(ctx, "template.caiProjectSize").Int()) {
|
|
|
|
+ vv := v.(*BidDataDetail)
|
|
|
|
+ content += fmt.Sprintf("<br>项目%s:%s", NumToChinese(k+1), vv.ProjectName)
|
|
|
|
+ content += fmt.Sprintf("<br>项目地区:%s", vv.Area)
|
|
|
|
+ if vv.Buyer != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>采购单位:%s", vv.Buyer)
|
|
|
|
+ }
|
|
|
|
+ if vv.Budget != "" && vv.Budget != "0" {
|
|
|
|
+ content += fmt.Sprintf("<br>预算金额:%s", vv.Budget)
|
|
|
|
+ }
|
|
|
|
+ if vv.PurchaseTime != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>预计采购时间:%s", vv.PurchaseTime)
|
|
|
|
+ }
|
|
|
|
+ if vv.Detail != "" {
|
|
|
|
+ content += fmt.Sprintf("<br>需求概况:%s", vv.Detail)
|
|
|
|
+ }
|
|
|
|
+ content += "<br>"
|
|
|
|
+ }
|
|
|
|
+ content = g.Config().MustGet(ctx, "template.yxsjgs.content").String() + content
|
|
|
|
+ articles = append(articles, &Article{
|
|
|
|
+ Title: fmt.Sprintf("%s_%s_采购意向", ymd, kk),
|
|
|
|
+ Content: content,
|
|
|
|
+ })
|
|
|
|
+ }
|
|
|
|
+ return true
|
|
|
|
+ })
|
|
|
|
+ //
|
|
|
|
+ if len(articles) > 0 {
|
|
|
|
+ list := g.List{}
|
|
|
|
+ for _, v := range articles {
|
|
|
|
+ list = append(list, g.Map{
|
|
|
|
+ "article_type": "news",
|
|
|
|
+ "title": v.Title,
|
|
|
|
+ //"author":AUTHOR,
|
|
|
|
+ //"digest":DIGEST,
|
|
|
|
+ "content": v.Content,
|
|
|
|
+ //"content_source_url":CONTENT_SOURCE_URL,
|
|
|
|
+ "thumb_media_id": g.Config().MustGet(ctx, "mediaId").String(),
|
|
|
|
+ //"need_open_comment":0,
|
|
|
|
+ //"only_fans_can_comment":0,
|
|
|
|
+ //"pic_crop_235_1":X1_Y1_X2_Y2,
|
|
|
|
+ //"pic_crop_1_1":X1_Y1_X2_Y2
|
|
|
|
+ })
|
|
|
|
+ }
|
|
|
|
+ g.Log().Info(ctx, "提交草稿数据", len(articles), "条", gconv.String(list))
|
|
|
|
+ result, err := g.Client().ContentType("application/json").Post(ctx, "https://api.weixin.qq.com/cgi-bin/draft/add?access_token="+getAccessToken(ctx), g.Map{"articles": list})
|
|
|
|
+ if err != nil {
|
|
|
|
+ g.Log().Error(ctx, "提交草稿出错", err)
|
|
|
|
+ return
|
|
|
|
+ }
|
|
|
|
+ defer result.Close()
|
|
|
|
+ g.Log().Info(ctx, "新增草稿箱请求返回结果", result.ReadAllString())
|
|
|
|
+ } else {
|
|
|
|
+ g.Log().Info(ctx, "没有需要提交草稿的数据")
|
|
|
|
+ }
|
|
|
|
+ g.Log().Info(ctx, "新增草稿箱任务结束。。。")
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+func getAccessToken(ctx context.Context) string {
|
|
|
|
+ code := g.Config().MustGet(ctx, "appid").String()
|
|
|
|
+ var repl string
|
|
|
|
+ client, err := rpc.DialHTTP("tcp", g.Config().MustGet(ctx, "wxTokenRpc").String())
|
|
|
|
+ if err != nil {
|
|
|
|
+ g.Log().Error(ctx, code, err)
|
|
|
|
+ return repl
|
|
|
|
+ }
|
|
|
|
+ defer client.Close()
|
|
|
|
+ err = client.Call("WxTokenRpc.GetAccessToken", code, &repl)
|
|
|
|
+ if err != nil {
|
|
|
|
+ g.Log().Error(ctx, code, err)
|
|
|
|
+ return repl
|
|
|
|
+ }
|
|
|
|
+ if repl == "" {
|
|
|
|
+ g.Log().Error(ctx, code, "未获取到accessToken")
|
|
|
|
+ } else {
|
|
|
|
+ g.Log().Info(ctx, code, "获取到accessToken", repl)
|
|
|
|
+ }
|
|
|
|
+ return repl
|
|
|
|
+}
|
|
|
|
+func filterHtml(text string) string {
|
|
|
|
+ text = strings.ReplaceAll(text, `\t`, "")
|
|
|
|
+ text = strings.ReplaceAll(text, `\n`, "")
|
|
|
|
+ doc, err := html.Parse(strings.NewReader(text))
|
|
|
|
+ if err != nil {
|
|
|
|
+ return regexp.MustCompile(`<[^>]+>`).ReplaceAllString(text, "")
|
|
|
|
+ }
|
|
|
|
+ var textBuilder strings.Builder
|
|
|
|
+ var traverse func(*html.Node)
|
|
|
|
+ traverse = func(n *html.Node) {
|
|
|
|
+ if n.Type == html.TextNode {
|
|
|
|
+ textBuilder.WriteString(n.Data)
|
|
|
|
+ }
|
|
|
|
+ for c := n.FirstChild; c != nil; c = c.NextSibling {
|
|
|
|
+ traverse(c)
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ traverse(doc)
|
|
|
|
+ return strings.TrimSpace(textBuilder.String())
|
|
|
|
+}
|