30分钟快速编码-beego开发要闻直播推送 - Go语言中文社区

30分钟快速编码-beego开发要闻直播推送


需求

1.windows端实时推送
2.因为是股市要闻,实时要求间隔5s~30s
3.弹窗可定制,不影响正常看盘

信息源

1.雪球要闻直播
2.快兰斯24小时财经直播http://m.fbecn.com
3.东方财富研报

实现思路

客户端推送工具,以前rss非常流行,能不能通过rss客户端去实现这个效果,这样就能节省下许多工作量,到github.com上查了下,找到了个FeedNotifier

效果
image.png

推送效果.png

FeedNotifier用得是atom和rss协议,知道协议就好办,只要爬取新闻源并转换为atom协议内容即可

配置FeedNotifier
image.png
解析新闻源
雪球
快兰斯24小时财经直播
东方财富-研报直播
开始编码

创建路由,router.go

package routers

import (
    "majornews/controllers"

    "github.com/astaxie/beego"
)

func init() {
    beego.Router("/", &controllers.MainController{})
    beego.Router("/majornews", &controllers.MajorNewsController{})
    beego.Router("/emoneylive", &controllers.EMoneyLiveController{})
}

controllers/majornews.go

package controllers

import (
    "majornews/models"

    "github.com/astaxie/beego"
)

type MajorNewsController struct {
    beego.Controller
}

func (c *MajorNewsController) Get() {
    c.Ctx.WriteString(models.MajorNewsContent)
}

解析雪球要闻直播

package models

import (
    "bytes"
    "fmt"
    "os/exec"
    "time"

    "github.com/buger/jsonparser"
    "github.com/gorilla/feeds"

    "github.com/astaxie/beego/logs"
)

func init() {
    logs.Info("初始化雪球爬虫引擎.")
}

var MajorNewsContent string
var Sendedlist map[string]bool = make(map[string]bool)
var UseMac bool = false

func FetchMajorNewsLive() string {
    logs.Info("爬取新的一份要闻.")
    myfetcher := NewFetcher("xueqiu.com")
    myfetcher.Get("/") //news session
    newsReq, newsBody, err := myfetcher.Get("https://xueqiu.com/v4/statuses/user_timeline.json?page=1&user_id=5124430882")
    if err != nil {
        logs.Error(err)
    }
    if newsReq.StatusCode == 200 {
        logs.Info("get news.")
    }

    now := time.Now()
    feed := &feeds.Feed{
        Title:       "啊菜要闻直播",
        Link:        &feeds.Link{Href: "https://xueqiu.com/u/5124430882"},
        Description: "直播股市要闻",
        Author:      &feeds.Author{Name: "要闻直播", Email: "suixin@xueqiu.com"},
        Created:     now,
    }
    feed.Items = []*feeds.Item{}
    jsonparser.ArrayEach(newsBody, func(value []byte, dataType jsonparser.ValueType, offset int, err error) {
        m1, _, _, _ := jsonparser.Get(value, "target")
        m2, _, _, _ := jsonparser.Get(value, "text")
        // m3, _, _, _ := jsonparser.Get(value, "description")
        m4, _, _, _ := jsonparser.Get(value, "id")
        var m0 int64
        if mdata, err := jsonparser.GetInt(value, "created_at"); err == nil {
            m0 = mdata
        }
        // m0, _, _, _ := jsonparser.Get(value, "created_at")

        item := &feeds.Item{}
        item.Title = "发表于" + time.Unix(m0/1000, 0).Format("2006-01-02 15:04:05")
        targeturl := fmt.Sprintf("%s%s", "https://xueqiu.com", string(m1))
        item.Link = &feeds.Link{Href: targeturl}
        item.Description = string(m2)
        item.Author = &feeds.Author{Name: "要闻直播", Email: "suixin@xueqiu.com"}
        fmt.Println("时间戳:", m0)
        item.Created = time.Unix(m0/1000, 0)
        feed.Items = append(feed.Items, item)
        //mac的消息通知
        if UseMac {
            id := string(m4)
            titlestr := "发表于" + time.Unix(m0/1000, 0).Format("2006-01-02 15:04:05")
            msg := string(m2)
            if _, ok := Sendedlist[id]; !ok {
                Sendedlist[id] = false
            }
            SendToNotificationCenter(id, titlestr, msg, targeturl)
        }
    }, "statuses")
    atom, _ := feed.ToAtom()
    // fmt.Println(atom)
    MajorNewsContent = atom
    return MajorNewsContent
}

//发送到mac通知中心
func SendToNotificationCenter(id string, titlestr string, msg string, targeturl string) {
    if issend, ok := Sendedlist[id]; ok && !issend {
        // fmt.Println("未发送,执行发送")
        cmdstr := `terminal-notifier -title '` + titlestr + `' -message '` + msg + `' -open '` + targeturl + `' -sound default -contentImage https://xavatar.imedao.com/community/201711/1513595963954-1513595964287.png`
        exec_shell(cmdstr)
        Sendedlist[id] = true
    }

}

func exec_shell(s string) {
    cmd := exec.Command("/bin/bash", "-c", s)
    var out bytes.Buffer

    cmd.Stdout = &out
    err := cmd.Run()
    if err != nil {
        logs.Error(err)
    }
    // fmt.Printf("%s", out.String())
}

func subString(str string, begin, length int) (substr string) {
    // 将字符串的转换成[]rune
    rs := []rune(str)
    lth := len(rs)

    // 简单的越界判断
    if begin < 0 {
        begin = 0
    }
    if begin >= lth {
        begin = lth
    }
    end := begin + length
    if end > lth {
        end = lth
    }

    // 返回子串
    return string(rs[begin:end])
}

定时爬取新闻源

package main

import (
    "majornews/models"
    _ "majornews/routers"

    "github.com/astaxie/beego"
    "github.com/astaxie/beego/logs"
    "github.com/astaxie/beego/toolbox"
)

func init() {
    logs.SetLogger(logs.AdapterConsole, `{"filename":"project.log","level":7,"maxlines":0,"maxsize":0,"daily":true,"maxdays":10}`)
    logs.Info("雪球要闻直播初始化")
    models.FetchMajorNewsLive()
    models.FetchRoom()
    intervalstr := "0/5 * * * * *"
    tk_xueqiu := toolbox.NewTask("tk_xueqiu", intervalstr, func() error { models.FetchMajorNewsLive(); return nil })
    toolbox.AddTask("tk_xueqiu", tk_xueqiu)
    toolbox.StartTask()
}

func main() {
    logs.Info("直播开始,只保留最新的20条数据")
    beego.Run()
}

编译完成后部署到服务器上即可

需要带超预期研报推送工具的可以加入知识星球获取


扫二维码交流

扫描进入知识星球
版权声明:本文来源简书,感谢博主原创文章,遵循 CC 4.0 by-sa 版权协议,转载请附上原文出处链接和本声明。
原文链接:https://www.jianshu.com/p/bdc4d88e0ed0
站方申明:本站部分内容来自社区用户分享,若涉及侵权,请联系站方删除。
  • 发表于 2020-01-12 11:59:01
  • 阅读 ( 1843 )
  • 分类:Go

0 条评论

请先 登录 后评论

官方社群

GO教程

猜你喜欢