timegraph_client/
lib.rs

1use crate::query::{CollectData, ResponseData, Variables};
2use anyhow::{anyhow, Context, Result};
3use graphql_client::{GraphQLQuery, Response};
4use reqwest::header::AUTHORIZATION;
5use reqwest::Client;
6
7mod query;
8
9const TW_LOG: &str = "timegraph";
10
11#[derive(Clone, Debug)]
12pub struct TimegraphData {
13    /// collection hashId
14    pub collection: String,
15    /// task associated with data
16    pub task_id: u64,
17    /// for repeated task it's incremented on every run
18    pub task_cycle: u64,
19    /// target network block number
20    pub target_block_number: u64,
21    /// time-chain block number
22    pub timechain_block_number: u64,
23    /// Shard identifier
24    pub shard_id: u64,
25    /// TSS signature
26    pub signature: [u8; 64],
27    /// data to add into collection
28    pub data: Vec<String>,
29}
30
31pub struct Timegraph {
32    client: Client,
33    url: String,
34    ssk: String,
35}
36
37impl Timegraph {
38    pub fn new(url: String, ssk: String) -> Result<Self> {
39        let client = Client::new();
40        Ok(Self { client, url, ssk })
41    }
42
43    /// Add data into collection (user must have Collector role)
44    pub async fn submit_data(&self, data: TimegraphData) -> Result<()> {
45        let variables = Variables {
46            feed: data.collection,
47            task_id: data.task_id as _,
48            task_cycle: data.task_cycle as _,
49            target_block: data.target_block_number as _,
50            timechain_block: data.timechain_block_number as _,
51            shard_id: data.shard_id as _,
52            signature: hex::encode(data.signature),
53            data: data.data,
54        };
55
56        let request = CollectData::build_query(variables);
57        let response = self
58            .client
59            .post(&self.url)
60            .json(&request)
61            .header(AUTHORIZATION, &self.ssk)
62            .send()
63            .await
64            .map_err(|e| anyhow!("error post to timegraph {e}"))?;
65        let json = response
66            .json::<Response<ResponseData>>()
67            .await
68            .map_err(|e| anyhow!("Failed to parse timegraph response {e}"))?;
69        let data = json.data.context(format!(
70            "timegraph migrate collect status fail: No reponse {:?}",
71            json.errors
72        ))?;
73        log::info!(
74            target: TW_LOG,
75            "timegraph migrate collect status: {:?}",
76            data.collect.status
77        );
78        Ok(())
79    }
80}