mirror of
https://github.com/ArvinLovegood/go-stock.git
synced 2025-07-19 00:00:09 +08:00
feat(frontend):个股卡片中添加按钮,可以直接跳转到个股研报和公司公告页面,查询对应个股的研报或公告
- 在 market.vue 中添加个股研报和公司公告组件 - 在 stock.vue 中增加研报和公告的搜索功能 - 修改 StockNoticeList 和 StockResearchReportList 组件,支持接收 stockCode 参数 - 在 backend 中添加 TradingView 新闻 API 接口
This commit is contained in:
parent
f6d217e4fd
commit
a936dc6371
@ -425,6 +425,15 @@ func (m MarketNewsApi) StockResearchReport(stockCode string, days int) []any {
|
||||
if strutil.ContainsAny(stockCode, []string{"."}) {
|
||||
stockCode = strings.Split(stockCode, ".")[0]
|
||||
beginDate = time.Now().Add(-time.Duration(days) * 365 * time.Hour).Format("2006-01-02")
|
||||
} else {
|
||||
stockCode = strutil.ReplaceWithMap(stockCode, map[string]string{
|
||||
"sh": "",
|
||||
"sz": "",
|
||||
"gb_": "",
|
||||
"us": "",
|
||||
"us_": "",
|
||||
})
|
||||
beginDate = time.Now().Add(-time.Duration(days) * 365 * time.Hour).Format("2006-01-02")
|
||||
}
|
||||
|
||||
logger.SugaredLogger.Infof("StockResearchReport-stockCode:%s", stockCode)
|
||||
@ -481,6 +490,15 @@ func (m MarketNewsApi) StockNotice(stock_list string) []any {
|
||||
if strutil.ContainsAny(stockCode, []string{"."}) {
|
||||
stockCode = strings.Split(stockCode, ".")[0]
|
||||
stockCodes = append(stockCodes, stockCode)
|
||||
} else {
|
||||
stockCode = strutil.ReplaceWithMap(stockCode, map[string]string{
|
||||
"sh": "",
|
||||
"sz": "",
|
||||
"gb_": "",
|
||||
"us": "",
|
||||
"us_": "",
|
||||
})
|
||||
stockCodes = append(stockCodes, stockCode)
|
||||
}
|
||||
}
|
||||
|
||||
@ -530,3 +548,29 @@ func (m MarketNewsApi) EMDictCode(code string, cache *freecache.Cache) []any {
|
||||
cache.Set([]byte(code), resp.Body(), 60*60*24)
|
||||
return respMap["data"].([]any)
|
||||
}
|
||||
|
||||
func (m MarketNewsApi) TradingViewNews() *[]models.TVNews {
|
||||
TVNews := &[]models.TVNews{}
|
||||
url := "https://news-mediator.tradingview.com/news-flow/v2/news?filter=lang:zh-Hans&filter=provider:panews,reuters&client=screener&streaming=false"
|
||||
resp, err := resty.New().SetProxy("http://127.0.0.1:10809").SetTimeout(time.Duration(30)*time.Second).R().
|
||||
SetHeader("Host", "news-mediator.tradingview.com").
|
||||
SetHeader("Origin", "https://cn.tradingview.com").
|
||||
SetHeader("Referer", "https://cn.tradingview.com/").
|
||||
SetHeader("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:140.0) Gecko/20100101 Firefox/140.0").
|
||||
Get(url)
|
||||
if err != nil {
|
||||
logger.SugaredLogger.Errorf("TradingViewNews err:%s", err.Error())
|
||||
return TVNews
|
||||
}
|
||||
respMap := map[string]any{}
|
||||
err = json.Unmarshal(resp.Body(), &respMap)
|
||||
if err != nil {
|
||||
return TVNews
|
||||
}
|
||||
items, err := json.Marshal(respMap["items"])
|
||||
if err != nil {
|
||||
return TVNews
|
||||
}
|
||||
json.Unmarshal(items, TVNews)
|
||||
return TVNews
|
||||
}
|
||||
|
@ -100,3 +100,11 @@ func TestEMDictCode(t *testing.T) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
func TestTradingViewNews(t *testing.T) {
|
||||
db.Init("../../data/stock.db")
|
||||
resp := NewMarketNewsApi().TradingViewNews()
|
||||
for _, a := range *resp {
|
||||
logger.SugaredLogger.Debugf("value: %+v", a)
|
||||
}
|
||||
}
|
||||
|
@ -2,6 +2,7 @@ package data
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"strings"
|
||||
"testing"
|
||||
)
|
||||
|
||||
@ -19,6 +20,10 @@ func TestAnalyzeSentiment(t *testing.T) {
|
||||
//text = " 【三大指数均跌逾1% 下跌个股近4800只】财联社6月19日电,指数持续走弱,沪指下挫跌逾1.00%,深成指跌1.25%,创业板指跌1.39%。核聚变、风电、军工、食品消费等板块指数跌幅居前,沪深京三市下跌个股近4800只。\n"
|
||||
text = "【银行理财首单网下打新落地】财联社6月20日电,记者从多渠道获悉,光大理财以申报价格17元参与信通电子网下打新,并成功入围有效报价,成为行业内首家参与网下打新的银行理财公司。光大理财工作人员向证券时报记者表示,本次光大理财是以其管理的混合类产品“阳光橙增盈绝对收益策略”参与了此次网下打新,该产品为光大理财“固收+”银行理财产品。资料显示,信通电子成立于1996年,核心产品包括输电线路智能巡检系统、变电站智能辅控系统、移动智能终端及其他产品。根据其招股说明书,信通电子2023、2024年营业收入分别较上年增长19.08%和7.97%,净利润分别较上年增长5.6%和15.11%。 (证券时报)"
|
||||
text = " 【以军称拦截数枚伊朗导弹】财联社6月20日电,据央视新闻报道,以军在贝尔谢巴及周边区域拦截了数枚伊朗导弹,但仍有导弹或拦截残骸落地。以色列国防军发文表示,搜救队伍正在一处“空中物体落地”的所在区域开展工作,公众目前可以离开避难场所。伊朗方面对上述说法暂无回应。"
|
||||
|
||||
words := splitWords(text)
|
||||
fmt.Println(strings.Join(words, " "))
|
||||
|
||||
result := AnalyzeSentiment(text)
|
||||
|
||||
// 输出结果
|
||||
|
@ -303,3 +303,17 @@ type LongTigerRankData struct {
|
||||
func (l LongTigerRankData) TableName() string {
|
||||
return "long_tiger_rank"
|
||||
}
|
||||
|
||||
type TVNews struct {
|
||||
Id string `json:"id"`
|
||||
Title string `json:"title"`
|
||||
Published int `json:"published"`
|
||||
Urgency int `json:"urgency"`
|
||||
Permission string `json:"permission"`
|
||||
StoryPath string `json:"storyPath"`
|
||||
Provider struct {
|
||||
Id string `json:"id"`
|
||||
Name string `json:"name"`
|
||||
LogoId string `json:"logo_id"`
|
||||
} `json:"provider"`
|
||||
}
|
||||
|
@ -6,11 +6,20 @@ import {RefreshCircleSharp} from "@vicons/ionicons5";
|
||||
import _ from "lodash";
|
||||
import KLineChart from "./KLineChart.vue";
|
||||
import MoneyTrend from "./moneyTrend.vue";
|
||||
import {useMessage} from "naive-ui";
|
||||
|
||||
const {stockCode}=defineProps(
|
||||
{
|
||||
stockCode: {
|
||||
type: String,
|
||||
default: ''
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
const list = ref([])
|
||||
const options = ref([])
|
||||
|
||||
const message=useMessage()
|
||||
function getNotice(stockCodes) {
|
||||
StockNotice(stockCodes).then(result => {
|
||||
console.log(result)
|
||||
@ -19,7 +28,8 @@ function getNotice(stockCodes) {
|
||||
}
|
||||
|
||||
onBeforeMount (()=>{
|
||||
getNotice('');
|
||||
//message.info("正在获取数据"+stockCode)
|
||||
getNotice(stockCode);
|
||||
})
|
||||
|
||||
function findStockList(query){
|
||||
|
@ -8,6 +8,15 @@ import MoneyTrend from "./moneyTrend.vue";
|
||||
import {useMessage} from "naive-ui";
|
||||
import {BrowserOpenURL} from "../../wailsjs/runtime";
|
||||
|
||||
const {stockCode}=defineProps(
|
||||
{
|
||||
stockCode: {
|
||||
type: String,
|
||||
default: ''
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
const message=useMessage()
|
||||
const list = ref([])
|
||||
|
||||
@ -21,7 +30,7 @@ function getStockResearchReport(value) {
|
||||
}
|
||||
|
||||
onBeforeMount(()=>{
|
||||
getStockResearchReport('');
|
||||
getStockResearchReport(stockCode);
|
||||
})
|
||||
|
||||
function ratingChangeName(ratingChange){
|
||||
|
@ -63,6 +63,7 @@ const sort = ref("0")
|
||||
const nowTab = ref("市场快讯")
|
||||
const indexInterval = ref(null)
|
||||
const indexIndustryRank = ref(null)
|
||||
const stockCode= ref('')
|
||||
|
||||
function getIndex() {
|
||||
GlobalStockIndexes().then((res) => {
|
||||
@ -79,6 +80,7 @@ function getIndex() {
|
||||
|
||||
onBeforeMount(() => {
|
||||
nowTab.value = route.query.name
|
||||
stockCode.value = route.query.stockCode
|
||||
GetConfig().then(result => {
|
||||
summaryBTN.value = result.openAiEnable
|
||||
darkTheme.value = result.darkTheme
|
||||
@ -547,10 +549,10 @@ function ReFlesh(source) {
|
||||
<LongTigerRankList />
|
||||
</n-tab-pane>
|
||||
<n-tab-pane name="个股研报" tab="个股研报">
|
||||
<StockResearchReportList/>
|
||||
<StockResearchReportList :stock-code="stockCode"/>
|
||||
</n-tab-pane>
|
||||
<n-tab-pane name="公司公告" tab="公司公告 ">
|
||||
<StockNoticeList/>
|
||||
<StockNoticeList :stock-code="stockCode" />
|
||||
</n-tab-pane>
|
||||
<n-tab-pane name="行业研究" tab="行业研究 ">
|
||||
<IndustryResearchReportList/>
|
||||
|
@ -1609,6 +1609,25 @@ function delStockGroup(code,name,groupId){
|
||||
message.info(result)
|
||||
})
|
||||
}
|
||||
|
||||
function searchNotice(stockCode){
|
||||
router.push({
|
||||
name: 'market',
|
||||
query: {
|
||||
name: '公司公告',
|
||||
stockCode: stockCode,
|
||||
},
|
||||
})
|
||||
}
|
||||
function searchStockReport(stockCode){
|
||||
router.push({
|
||||
name: 'market',
|
||||
query: {
|
||||
name: '个股研报',
|
||||
stockCode: stockCode,
|
||||
},
|
||||
})
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
@ -1711,22 +1730,25 @@ function delStockGroup(code,name,groupId){
|
||||
</template>
|
||||
<template #footer>
|
||||
<n-flex justify="center">
|
||||
<n-text :type="'info'">{{result["日期"]+" "+result["时间"]}}</n-text>
|
||||
<n-tag size="small" v-if="result.volume>0" :type="result.profitType">{{result.volume+"股"}}</n-tag>
|
||||
<n-tag size="small" v-if="result.costPrice>0" :type="result.profitType">{{"成本:"+result.costPrice+"*"+result.costVolume+" "+result.profit+"%"+" ( "+result.profitAmount+" ¥ )"}}</n-tag>
|
||||
</n-flex>
|
||||
</template>
|
||||
<template #action>
|
||||
<n-flex justify="space-between">
|
||||
<n-text :type="'info'">{{result["日期"]+" "+result["时间"]}}</n-text>
|
||||
<n-button size="tiny" type="info" @click="setStock(result['股票代码'],result['股票名称'])"> 成本 </n-button>
|
||||
<n-button size="tiny" type="success" @click="showFenshi(result['股票代码'],result['股票名称'],result.changePercent)"> 分时 </n-button>
|
||||
<n-flex justify="left">
|
||||
<n-button size="tiny" type="warning" @click="setStock(result['股票代码'],result['股票名称'])"> 成本 </n-button>
|
||||
<n-button size="tiny" type="error" @click="showFenshi(result['股票代码'],result['股票名称'],result.changePercent)"> 分时 </n-button>
|
||||
<n-button size="tiny" type="error" @click="showK(result['股票代码'],result['股票名称'])"> 日K </n-button>
|
||||
<n-button size="tiny" type="error" v-if="result['买一报价']>0" @click="showMoney(result['股票代码'],result['股票名称'])"> 资金 </n-button>
|
||||
|
||||
<n-button size="tiny" type="warning" @click="search(result['股票代码'],result['股票名称'])"> 详情 </n-button>
|
||||
<n-dropdown trigger="click" :options="groupList" key-field="ID" label-field="name" @select="(groupId) => AddStockGroupInfo(groupId,result['股票代码'],result['股票名称'])">
|
||||
<n-button type="success" size="tiny">设置分组</n-button>
|
||||
</n-dropdown>
|
||||
<n-button size="tiny" type="success" @click="search(result['股票代码'],result['股票名称'])"> 详情 </n-button>
|
||||
<n-button v-if="result['买一报价']>0" size="tiny" type="success" @click="searchNotice(result['股票代码'])"> 公告 </n-button>
|
||||
<n-button v-if="result['买一报价']>0" size="tiny" type="success" @click="searchStockReport(result['股票代码'])"> 研报 </n-button>
|
||||
<n-flex justify="right">
|
||||
<n-dropdown trigger="click" :options="groupList" key-field="ID" label-field="name" @select="(groupId) => AddStockGroupInfo(groupId,result['股票代码'],result['股票名称'])">
|
||||
<n-button type="warning" size="tiny">设置分组</n-button>
|
||||
</n-dropdown>
|
||||
</n-flex>
|
||||
</n-flex>
|
||||
</template>
|
||||
</n-card >
|
||||
@ -1824,23 +1846,25 @@ function delStockGroup(code,name,groupId){
|
||||
</template>
|
||||
<template #footer>
|
||||
<n-flex justify="center">
|
||||
<n-text :type="'info'">{{result["日期"]+" "+result["时间"]}}</n-text>
|
||||
<n-tag size="small" v-if="result.volume>0" :type="result.profitType">{{result.volume+"股"}}</n-tag>
|
||||
<n-tag size="small" v-if="result.costPrice>0" :type="result.profitType">{{"成本:"+result.costPrice+"*"+result.costVolume+" "+result.profit+"%"+" ( "+result.profitAmount+" ¥ )"}}</n-tag>
|
||||
</n-flex>
|
||||
</template>
|
||||
<template #action>
|
||||
<n-flex justify="space-between">
|
||||
<n-text :type="'info'">{{result["日期"]+" "+result["时间"]}}</n-text>
|
||||
<n-button size="tiny" type="info" @click="setStock(result['股票代码'],result['股票名称'])"> 成本 </n-button>
|
||||
<n-button size="tiny" type="success" @click="showFenshi(result['股票代码'],result['股票名称'],result.changePercent)"> 分时 </n-button>
|
||||
<n-flex justify="left">
|
||||
<n-button size="tiny" type="warning" @click="setStock(result['股票代码'],result['股票名称'])"> 成本 </n-button>
|
||||
<n-button size="tiny" type="error" @click="showFenshi(result['股票代码'],result['股票名称'],result.changePercent)"> 分时 </n-button>
|
||||
<n-button size="tiny" type="error" @click="showK(result['股票代码'],result['股票名称'])"> 日K </n-button>
|
||||
<n-button size="tiny" type="error" v-if="result['买一报价']>0" @click="showMoney(result['股票代码'],result['股票名称'])"> 资金 </n-button>
|
||||
|
||||
<n-button size="tiny" type="warning" @click="search(result['股票代码'],result['股票名称'])"> 详情 </n-button>
|
||||
<n-dropdown trigger="click" :options="groupList" key-field="ID" label-field="name" @select="(groupId) => AddStockGroupInfo(groupId,result['股票代码'],result['股票名称'])">
|
||||
<n-button type="success" size="tiny">设置分组</n-button>
|
||||
</n-dropdown>
|
||||
|
||||
<n-button size="tiny" type="success" @click="search(result['股票代码'],result['股票名称'])"> 详情 </n-button>
|
||||
<n-button v-if="result['买一报价']>0" size="tiny" type="success" @click="searchNotice(result['股票代码'])"> 公告 </n-button>
|
||||
<n-button v-if="result['买一报价']>0" size="tiny" type="success" @click="searchStockReport(result['股票代码'])"> 研报 </n-button>
|
||||
<n-flex justify="right">
|
||||
<n-dropdown trigger="click" :options="groupList" key-field="ID" label-field="name" @select="(groupId) => AddStockGroupInfo(groupId,result['股票代码'],result['股票名称'])">
|
||||
<n-button type="warning" size="tiny">设置分组</n-button>
|
||||
</n-dropdown>
|
||||
</n-flex>
|
||||
</n-flex>
|
||||
</template>
|
||||
</n-card >
|
||||
|
Loading…
x
Reference in New Issue
Block a user