Skip to main content

bolt_cw_sdk/oracle/
update_config.rs

1use cosmrs::cosmwasm::MsgExecuteContract;
2use cosmrs::tx::Msg;
3use cosmwasm_std::Decimal256;
4use serde::Serialize;
5
6use crate::oracle::client::OracleAdminClient;
7use crate::oracle::error::OracleError;
8use crate::tx_builder::TxBuilder;
9
10impl OracleAdminClient {
11    pub fn append_update_config_msg(
12        &self,
13        tx_builder: &mut TxBuilder,
14        price_threshold_ratio: Option<Decimal256>,
15        price_expire_millis: Option<u64>,
16    ) -> Result<(), OracleError> {
17        let update_config = UpdateConfig {
18            price_threshold_ratio,
19            price_expire_millis,
20        };
21        let contract_msg = ExecuteMsg { update_config };
22        let contract_msg =
23            serde_json::to_vec(&contract_msg).map_err(OracleError::SerdeJsonError)?;
24        let msg = MsgExecuteContract {
25            sender: tx_builder.account_id.clone(),
26            contract: self.chain_config.oracle_contract_address.clone(),
27            msg: contract_msg,
28            funds: vec![],
29        };
30        let msg = msg.to_any().map_err(OracleError::EyreError)?;
31
32        tx_builder.add_msg(msg);
33        Ok(())
34    }
35}
36
37#[derive(Serialize)]
38pub struct UpdateConfig {
39    pub price_threshold_ratio: Option<Decimal256>,
40    pub price_expire_millis: Option<u64>,
41}
42
43#[derive(Serialize)]
44struct ExecuteMsg {
45    pub update_config: UpdateConfig,
46}
47
48#[cfg(test)]
49mod tests {
50    use std::str::FromStr;
51
52    use cosmrs::tendermint::abci::Code;
53    use serial_test::serial;
54
55    use super::*;
56    use crate::test_utils::helpers::assert_event_attribute;
57    use crate::test_utils::test_scenario::TestScenario;
58
59    #[tokio::test]
60    #[serial]
61    async fn test_update_config() {
62        let test_scenario = TestScenario::new_from_config("config.json".to_string()).await;
63
64        let price_threshold_ratio = Decimal256::from_str("0.5").unwrap();
65        let price_expire_millis = Some(1000);
66        let oracle_contract_address = test_scenario
67            .instantiate_oracle_contract(price_threshold_ratio, price_expire_millis)
68            .await;
69
70        let client = OracleAdminClient::from_scenario(&test_scenario, &oracle_contract_address)
71            .expect("Failed to create oracle admin client");
72
73        let account = client
74            .public_oracle_client
75            .account(test_scenario.admin_address.clone())
76            .await
77            .expect("Failed to get account from public oracle client");
78        let mut tx_builder = TxBuilder::new(
79            test_scenario.admin_mnemonic.clone(),
80            test_scenario.chain_prefix.clone(),
81            test_scenario.chain_id.clone(),
82            test_scenario.derivation_path,
83            account.sequence,
84            account.account_number,
85        )
86        .expect("Failed to create tx builder");
87
88        let price_threshold_ratio = Decimal256::one();
89        let price_expire_millis = 42;
90        client
91            .append_update_config_msg(
92                &mut tx_builder,
93                Some(price_threshold_ratio),
94                Some(price_expire_millis),
95            )
96            .unwrap();
97
98        tx_builder.set_memo("From test_update_config".to_string());
99        let gas = 500_000u64;
100        tx_builder.set_fee(70_000_000_000_000_000u128, &test_scenario.chain_denom, gas);
101        let signed_bytes = tx_builder
102            .get_signed_bytes()
103            .expect("Failed to get signed bytes");
104
105        let response = client
106            .broadcast_tx(signed_bytes)
107            .await
108            .expect("Failed to broadcast tx");
109
110        match response.tx_result.code {
111            Code::Ok => {
112                println!("Transaction successful: {:?}", response.hash);
113                let update_config_event = response
114                    .tx_result
115                    .events
116                    .iter()
117                    .find(|ev| ev.kind == "wasm-update_config")
118                    .expect("Failed to find update config event");
119                assert_event_attribute(
120                    update_config_event,
121                    "price_expire_millis",
122                    &price_expire_millis.to_string(),
123                );
124                assert_event_attribute(
125                    update_config_event,
126                    "price_threshold_ratio",
127                    &price_threshold_ratio.to_string(),
128                );
129            }
130            Code::Err(code) => {
131                panic!(
132                    "Transaction failed with code: {:?} response: {:?}",
133                    code, response
134                );
135            }
136        }
137    }
138}