Skip to main content

futucli/cmd/
rt.rs

1//! `futucli rt` — 获取分时数据
2
3use std::time::Duration;
4
5use anyhow::Result;
6use serde::Serialize;
7use tabled::Tabled;
8
9use crate::common::{connect_gateway, parse_symbol};
10use crate::output::OutputFormat;
11use futu_qot::types::SubType;
12
13#[derive(Tabled)]
14struct RtRow {
15    #[tabled(rename = "Time")]
16    time: String,
17    #[tabled(rename = "Price")]
18    price: String,
19    #[tabled(rename = "Avg")]
20    avg: String,
21    #[tabled(rename = "Volume")]
22    volume: String,
23    #[tabled(rename = "Turnover")]
24    turnover: String,
25}
26
27#[derive(Serialize)]
28struct RtJson {
29    time: String,
30    minute: i32,
31    is_blank: bool,
32    price: f64,
33    last_close_price: f64,
34    avg_price: f64,
35    volume: i64,
36    turnover: f64,
37    timestamp: f64,
38}
39
40pub async fn run(gateway: &str, symbol: &str, format: OutputFormat) -> Result<()> {
41    let sec = parse_symbol(symbol)?;
42    let (client, _push_rx) = connect_gateway(gateway, "futucli-rt").await?;
43
44    futu_qot::sub::subscribe(
45        &client,
46        std::slice::from_ref(&sec),
47        &[SubType::RT],
48        true,
49        true,
50    )
51    .await?;
52    tokio::time::sleep(Duration::from_millis(300)).await;
53
54    let result = futu_qot::rt::get_rt(&client, &sec).await?;
55
56    let rows: Vec<RtRow> = result
57        .rt_list
58        .iter()
59        .filter(|r| !r.is_blank)
60        .map(|r| RtRow {
61            time: r.time.clone(),
62            price: format!("{:.3}", r.price),
63            avg: format!("{:.3}", r.avg_price),
64            volume: r.volume.to_string(),
65            turnover: format!("{:.0}", r.turnover),
66        })
67        .collect();
68
69    let jsons: Vec<RtJson> = result
70        .rt_list
71        .iter()
72        .map(|r| RtJson {
73            time: r.time.clone(),
74            minute: r.minute,
75            is_blank: r.is_blank,
76            price: r.price,
77            last_close_price: r.last_close_price,
78            avg_price: r.avg_price,
79            volume: r.volume,
80            turnover: r.turnover,
81            timestamp: r.timestamp,
82        })
83        .collect();
84
85    format.print_rows(&rows, &jsons)?;
86    Ok(())
87}