import {StockHistoryChart} from "./StockHistoryChart" import {useEffect,useState} from "react" import {ApiError,request} from "@/lib/auth" import {Button} from "@/components/ui/button" import {Card,CardContent,CardHeader,CardTitle} from "@/components/ui/card" type Instrument={id:string;symbol:string;exchange:string;name:string;price:string;observed_at:string;received_at:string} type Sync={id:string;status:string;instrument_count:number;message:string;finished_at:string} export function MarketPanel({onSessionExpired,initialSymbol}:{onSessionExpired:()=>void;initialSymbol?:string}){ const [selected,setSelected]=useState(null) const [list,setList]=useState([]),[tasks,setTasks]=useState([]),[query,setQuery]=useState(initialSymbol??""),[error,setError]=useState(""),[busy,setBusy]=useState(false) function fail(e:unknown){if(e instanceof ApiError&&e.status===401)onSessionExpired();else setError(e instanceof Error?e.message:"行情读取失败")} async function load(){setBusy(true);setError("");try{const [stocks,runs]=await Promise.all([request(`/api/admin/v1/instruments?q=${encodeURIComponent(query)}`),request("/api/admin/v1/market/syncs")]);setList(stocks);setTasks(runs)}catch(e){fail(e)}finally{setBusy(false)}} useEffect(()=>{void load()},[]) return 沪深股票池 · 行情与日线

启用公开行情适配器后,后端启动即同步沪深股票,此后每五分钟更新。此接口用于开发研究,价格按供应商时间展示,休市或同步失败时保留上次快照。不会把抓取时间当成实时行情时间。

{e.preventDefault();void load()}}>setQuery(e.target.value)}/>
{error&&

{error}

}
{["股票","价格","行情时间"].map(v=>)}{list.map(v=>)}
{v}

{v.exchange}:{v.symbol}

{v.price==="0.00"?"无报价":v.price+" 元"}{new Date(v.observed_at).toLocaleString("zh-CN")}
{list.length===0&&

暂无同步数据,请检查系统设置中的行情源与同步记录。

}
{selected&&

{selected.name}

{selected.exchange}:{selected.symbol}

¥{selected.price}
}
最近同步记录
{tasks.length===0&&

还没有同步记录。

}{tasks.map(t=>
{new Date(t.finished_at).toLocaleString("zh-CN")} · {t.status==="COMPLETED"?`同步 ${t.instrument_count} 个证券`:t.message}
)}
}