pyth_sui_sdk/
read.rs

1//! JSON-RPC methods for querying Pyth on-chain data.
2use af_ptbuilder::ptb;
3use af_sui_types::{Address as SuiAddress, ObjectArg, TransactionKind};
4use sui_framework_sdk::object::ID;
5use sui_jsonrpc::api::WriteApiClient;
6use sui_sdk_types::bcs::{FromBcs, ToBcs};
7
8pub type Result<T> = std::result::Result<T, Error>;
9
10#[derive(thiserror::Error, Debug)]
11pub enum Error {
12    #[error(transparent)]
13    JsonRpcClient(#[from] sui_jsonrpc::error::JsonRpcClientError),
14    #[error("In ProgrammableTransactionBuilder: {0}")]
15    PtBuilder(#[from] af_ptbuilder::Error),
16    #[error(transparent)]
17    FromHex(#[from] hex::FromHexError),
18    #[error("Serializing to BCS: {0}")]
19    Bcs(#[from] sui_sdk_types::bcs::Error),
20    #[error("DevInspectResults.results is None")]
21    DevInspectResults,
22}
23
24/// Performs a dev-inspect with a client implementation to return the object ID for an off-chain
25/// price identifier.
26///
27/// Price identifiers can be found in <https://www.pyth.network/developers/price-feed-ids>
28pub async fn get_price_info_object_id_from_pyth_state<C>(
29    client: &C,
30    package: SuiAddress,
31    price_identifier_hex: String,
32    pyth_state: ObjectArg,
33) -> Result<SuiAddress>
34where
35    C: WriteApiClient + Sync,
36{
37    let price_identifier_bytes = &hex::decode(price_identifier_hex.replace("0x", ""))?;
38
39    let inspect_tx = ptb!(
40        package pyth: package;
41
42        input obj pyth_state;
43        input pure price_identifier_bytes;
44
45        pyth::state::get_price_info_object_id(pyth_state, price_identifier_bytes);
46    );
47
48    let mut results = {
49        let tx_bytes = TransactionKind::ProgrammableTransaction(inspect_tx).to_bcs_base64()?;
50        let resp = client
51            .dev_inspect_transaction_block(
52                SuiAddress::ZERO, // doesn't matter
53                tx_bytes,
54                None,
55                None,
56                None,
57            )
58            .await?;
59        resp.results.ok_or(Error::DevInspectResults)?
60    };
61    let sui_exec_result = results.swap_remove(0);
62    let mut return_values = sui_exec_result.return_values;
63    let (bytes, _sui_type_tag) = return_values.swap_remove(0);
64    let id = ID::from_bcs(&bytes)?;
65    Ok(id.bytes)
66}