mirror of
https://github.com/ArvinLovegood/go-stock.git
synced 2025-07-19 00:00:09 +08:00
feat(backend): 实现股票价格实时监控功能
- 在 App 结构中添加定时更新股票价格的逻辑 - 实现 MonitorStockPrices 函数,用于更新关注股票的价格 - 在前端添加股票价格更新的事件处理 - 优化股票数据的获取和处理逻辑
This commit is contained in:
parent
e7560f3e9b
commit
1554d3309d
54
app.go
54
app.go
@ -12,6 +12,7 @@ import (
|
||||
"go-stock/backend/data"
|
||||
"go-stock/backend/db"
|
||||
"go-stock/backend/logger"
|
||||
"time"
|
||||
)
|
||||
|
||||
// App struct
|
||||
@ -46,14 +47,51 @@ func (a *App) startup(ctx context.Context) {
|
||||
// domReady is called after front-end resources have been loaded
|
||||
func (a *App) domReady(ctx context.Context) {
|
||||
// Add your action here
|
||||
//ticker := time.NewTicker(time.Second)
|
||||
//defer ticker.Stop()
|
||||
////定时更新数据
|
||||
//go func() {
|
||||
// for range ticker.C {
|
||||
// runtime.WindowSetTitle(ctx, "go-stock "+time.Now().Format("2006-01-02 15:04:05"))
|
||||
// }
|
||||
//}()
|
||||
|
||||
//定时更新数据
|
||||
go func() {
|
||||
ticker := time.NewTicker(time.Second)
|
||||
defer ticker.Stop()
|
||||
for range ticker.C {
|
||||
runtime.WindowSetTitle(ctx, "go-stock "+time.Now().Format("2006-01-02 15:04:05"))
|
||||
}
|
||||
}()
|
||||
|
||||
//定时更新数据
|
||||
go func() {
|
||||
ticker := time.NewTicker(time.Second * 2)
|
||||
defer ticker.Stop()
|
||||
for range ticker.C {
|
||||
MonitorStockPrices(a)
|
||||
}
|
||||
}()
|
||||
}
|
||||
func MonitorStockPrices(a *App) {
|
||||
dest := &[]data.FollowedStock{}
|
||||
db.Dao.Model(&data.FollowedStock{}).Find(dest)
|
||||
for _, item := range *dest {
|
||||
follow := item
|
||||
stockCode := follow.StockCode
|
||||
go func() {
|
||||
stockData, err := data.NewStockDataApi().GetStockCodeRealTimeData(stockCode)
|
||||
if err != nil {
|
||||
logger.SugaredLogger.Errorf("get stock code real time data error:%s", err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
price, err := convertor.ToFloat(stockData.Price)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
if follow.Price != price {
|
||||
runtime.EventsEmit(a.ctx, "stock_price", stockData)
|
||||
go db.Dao.Model(follow).Where("stock_code = ?", stockCode).Updates(map[string]interface{}{
|
||||
"price": stockData.Price,
|
||||
})
|
||||
}
|
||||
|
||||
}()
|
||||
}
|
||||
}
|
||||
|
||||
// beforeClose is called when the application is about to quit,
|
||||
|
@ -268,13 +268,13 @@ func (receiver StockDataApi) GetStockCodeRealTimeData(StockCode string) (*StockI
|
||||
return &StockInfo{}, nil
|
||||
}
|
||||
stockData, err := ParseFullSingleStockData(GB18030ToUTF8(resp.Body()))
|
||||
var count int64
|
||||
db.Dao.Model(&StockInfo{}).Where("code = ?", StockCode).Count(&count)
|
||||
if count == 0 {
|
||||
go db.Dao.Model(&StockInfo{}).Create(stockData)
|
||||
} else {
|
||||
go db.Dao.Model(&StockInfo{}).Where("code = ?", StockCode).Updates(stockData)
|
||||
}
|
||||
//var count int64
|
||||
//db.Dao.Model(&StockInfo{}).Where("code = ?", StockCode).Count(&count)
|
||||
//if count == 0 {
|
||||
// go db.Dao.Model(&StockInfo{}).Create(stockData)
|
||||
//} else {
|
||||
// go db.Dao.Model(&StockInfo{}).Where("code = ?", StockCode).Updates(stockData)
|
||||
//}
|
||||
return stockData, err
|
||||
}
|
||||
|
||||
|
@ -84,7 +84,7 @@ onMounted(() => {
|
||||
|
||||
ticker.value=setInterval(() => {
|
||||
if(isTradingTime()){
|
||||
monitor()
|
||||
//monitor()
|
||||
data.fenshiURL='http://image.sinajs.cn/newchart/min/n/'+data.code+'.gif'+"?t="+Date.now()
|
||||
}
|
||||
}, 3500)
|
||||
@ -103,6 +103,10 @@ EventsOn("showSearch",(data)=>{
|
||||
addBTN.value = data === 1;
|
||||
})
|
||||
|
||||
EventsOn("stock_price",(data)=>{
|
||||
console.log("stock_price",data['股票代码'])
|
||||
updateData(data)
|
||||
})
|
||||
|
||||
EventsOn("refreshFollowList",(data)=>{
|
||||
|
||||
@ -183,6 +187,60 @@ function getStockList(value){
|
||||
}
|
||||
}
|
||||
|
||||
async function updateData(result) {
|
||||
if(result["当前价格"]<=0){
|
||||
result["当前价格"]=result["卖一报价"]
|
||||
}
|
||||
|
||||
let s=(result["当前价格"]-result["昨日收盘价"])*100/result["昨日收盘价"]
|
||||
let roundedNum = s.toFixed(2); // 将数字转换为保留两位小数的字符串形式
|
||||
result.s=roundedNum+"%"
|
||||
|
||||
result.highRate=((result["今日最高价"]-result["今日开盘价"])*100/result["今日开盘价"]).toFixed(2)+"%"
|
||||
result.lowRate=((result["今日最低价"]-result["今日开盘价"])*100/result["今日开盘价"]).toFixed(2)+"%"
|
||||
|
||||
if (roundedNum>0) {
|
||||
result.type="error"
|
||||
result.color="#E88080"
|
||||
}else if (roundedNum<0) {
|
||||
result.type="success"
|
||||
result.color="#63E2B7"
|
||||
}else {
|
||||
result.type="default"
|
||||
result.color="#FFFFFF"
|
||||
}
|
||||
let res= followList.value.filter(item => item.StockCode===result['股票代码'])
|
||||
if (res.length>0) {
|
||||
result.Sort=res[0].Sort
|
||||
result.costPrice=res[0].CostPrice
|
||||
result.volume=res[0].Volume
|
||||
result.profit=((result["当前价格"]-result.costPrice)*100/result.costPrice).toFixed(3)
|
||||
result.profitAmountToday=(result.volume*(result["当前价格"]-result["昨日收盘价"])).toFixed(2)
|
||||
result.profitAmount=(result.volume*(result["当前价格"]-result.costPrice)).toFixed(2)
|
||||
if(result.profitAmount>0){
|
||||
result.profitType="error"
|
||||
}else if(result.profitAmount<0){
|
||||
result.profitType="success"
|
||||
}
|
||||
if(result["当前价格"]){
|
||||
if(res[0].AlarmChangePercent>0&&Math.abs(roundedNum)>=res[0].AlarmChangePercent){
|
||||
SendMessage(result,1)
|
||||
}
|
||||
|
||||
if(res[0].AlarmPrice>0&&result["当前价格"]>=res[0].AlarmPrice){
|
||||
SendMessage(result,2)
|
||||
}
|
||||
|
||||
if(res[0].CostPrice>0&&result["当前价格"]>=res[0].CostPrice){
|
||||
SendMessage(result,3)
|
||||
}
|
||||
}
|
||||
}
|
||||
result.key=GetSortKey(result.Sort,result["股票代码"])
|
||||
results.value[GetSortKey(result.Sort,result["股票代码"])]=result
|
||||
}
|
||||
|
||||
|
||||
async function monitor() {
|
||||
for (let code of stocks.value) {
|
||||
// console.log(code)
|
||||
|
9
main.go
9
main.go
@ -44,8 +44,7 @@ func main() {
|
||||
if stocksBin != nil && len(stocksBin) > 0 {
|
||||
go initStockData()
|
||||
}
|
||||
go data.NewStockDataApi().GetStockBaseInfo()
|
||||
go data.NewStockDataApi().GetIndexBasic()
|
||||
//updateBasicInfo()
|
||||
|
||||
// Create an instance of the app structure
|
||||
app := NewApp()
|
||||
@ -141,6 +140,12 @@ func main() {
|
||||
|
||||
}
|
||||
|
||||
func updateBasicInfo() {
|
||||
//更新基本信息
|
||||
go data.NewStockDataApi().GetStockBaseInfo()
|
||||
go data.NewStockDataApi().GetIndexBasic()
|
||||
}
|
||||
|
||||
func initStockData() {
|
||||
var count int64
|
||||
db.Dao.Model(&data.StockBasic{}).Count(&count)
|
||||
|
Loading…
x
Reference in New Issue
Block a user