Skip to content

Commit

Permalink
Merge pull request #113 from pyth-network/push-nvlzuznkvoon
Browse files Browse the repository at this point in the history
feat!: allow loading network-specific PriceAccount
  • Loading branch information
Reisen authored Feb 9, 2024
2 parents 1acfc3d + 3a8c8e8 commit 096432f
Show file tree
Hide file tree
Showing 14 changed files with 298 additions and 45 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/pyth-sdk-example-anchor-contract.yml
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ jobs:
- name: Install solana binaries
run: |
# Installing 1.16.x cli tools to have sbf instead of bpf. bpf does not work anymore.
sh -c "$(curl -sSfL https://release.solana.com/v1.17.0/install)"
sh -c "$(curl -sSfL https://release.solana.com/v1.18.1/install)"
echo "/home/runner/.local/share/solana/install/active_release/bin" >> $GITHUB_PATH
- name: Install anchor binaries
run: |
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/pyth-sdk-example-solana-contract.yml
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ jobs:
- name: Install solana binaries
run: |
# Installing 1.16.x cli tools to have sbf instead of bpf. bpf does not work anymore.
sh -c "$(curl -sSfL https://release.solana.com/v1.17.0/install)"
sh -c "$(curl -sSfL https://release.solana.com/v1.18.1/install)"
echo "/home/runner/.local/share/solana/install/active_release/bin" >> $GITHUB_PATH
- name: Build
run: scripts/build.sh
2 changes: 1 addition & 1 deletion .github/workflows/pyth-sdk-solana.yml
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ jobs:
- name: Install Solana Binaries
run: |
# Installing 1.17.x cli tools to have sbf instead of bpf. bpf does not work anymore.
sh -c "$(curl -sSfL https://release.solana.com/v1.17.0/install)"
sh -c "$(curl -sSfL https://release.solana.com/v1.18.1/install)"
echo "/home/runner/.local/share/solana/install/active_release/bin" >> $GITHUB_PATH
- name: Build
run: cargo build --verbose
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,4 +19,4 @@ default = []
[dependencies]
anchor-lang = "0.28.0"
pyth-sdk = { path = "../../../../pyth-sdk", version = "0.8.0" }
pyth-sdk-solana = { path = "../../../../pyth-sdk-solana", version = "0.9.0" }
pyth-sdk-solana = { path = "../../../../pyth-sdk-solana", version = "0.10.0" }
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
use anchor_lang::prelude::*;
use pyth_sdk_solana::state::load_price_account;
use pyth_sdk_solana::state::SolanaPriceAccount;
use std::ops::Deref;
use std::str::FromStr;

Expand All @@ -25,7 +26,8 @@ impl anchor_lang::Owner for PriceFeed {

impl anchor_lang::AccountDeserialize for PriceFeed {
fn try_deserialize_unchecked(data: &mut &[u8]) -> Result<Self> {
let account = load_price_account(data).map_err(|_x| error!(ErrorCode::PythError))?;
let account: &SolanaPriceAccount =
load_price_account(data).map_err(|_x| error!(ErrorCode::PythError))?;

// Use a dummy key since the key field will be removed from the SDK
let zeros: [u8; 32] = [0; 32];
Expand Down
2 changes: 1 addition & 1 deletion examples/sol-contract/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -11,4 +11,4 @@ crate-type = ["cdylib", "lib"]
borsh = "0.10.3"
arrayref = "0.3.6"
solana-program = ">= 1.10"
pyth-sdk-solana = { path = "../../pyth-sdk-solana", version = "0.9.0" }
pyth-sdk-solana = { path = "../../pyth-sdk-solana", version = "0.10.0" }
10 changes: 5 additions & 5 deletions examples/sol-contract/src/processor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ use borsh::{
BorshDeserialize,
BorshSerialize,
};
use pyth_sdk_solana::load_price_feed_from_account_info;
use pyth_sdk_solana::state::SolanaPriceAccount;

use crate::instruction::ExampleInstructions;
use crate::state::AdminConfig;
Expand Down Expand Up @@ -53,8 +53,8 @@ pub fn process_instruction(
config.collateral_price_feed_id = *pyth_collateral_account.key;

// Make sure these Pyth price accounts can be loaded
load_price_feed_from_account_info(pyth_loan_account)?;
load_price_feed_from_account_info(pyth_collateral_account)?;
SolanaPriceAccount::account_info_to_feed(pyth_loan_account)?;
SolanaPriceAccount::account_info_to_feed(pyth_collateral_account)?;

let config_data = config.try_to_vec()?;
let config_dst = &mut admin_config_account.try_borrow_mut_data()?;
Expand Down Expand Up @@ -85,7 +85,7 @@ pub fn process_instruction(
// (price + conf) * loan_qty * 10 ^ (expo).
// Here is more explanation on confidence interval in Pyth:
// https://docs.pyth.network/consume-data/best-practices
let feed1 = load_price_feed_from_account_info(pyth_loan_account)?;
let feed1 = SolanaPriceAccount::account_info_to_feed(pyth_loan_account)?;
let current_timestamp1 = Clock::get()?.unix_timestamp;
let result1 = feed1
.get_price_no_older_than(current_timestamp1, 60)
Expand All @@ -107,7 +107,7 @@ pub fn process_instruction(
// (price - conf) * collateral_qty * 10 ^ (expo).
// Here is more explanation on confidence interval in Pyth:
// https://docs.pyth.network/consume-data/best-practices
let feed2 = load_price_feed_from_account_info(pyth_collateral_account)?;
let feed2 = SolanaPriceAccount::account_info_to_feed(pyth_collateral_account)?;
let current_timestamp2 = Clock::get()?.unix_timestamp;
let result2 = feed2
.get_price_no_older_than(current_timestamp2, 60)
Expand Down
2 changes: 1 addition & 1 deletion pyth-sdk-solana/Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "pyth-sdk-solana"
version = "0.9.0"
version = "0.10.0"
authors = ["Pyth Data Foundation"]
edition = "2018"
license = "Apache-2.0"
Expand Down
4 changes: 2 additions & 2 deletions pyth-sdk-solana/examples/eth_price.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
// example usage of reading pyth price from solana/pythnet price account

use pyth_sdk_solana::load_price_feed_from_account;
use pyth_sdk_solana::state::SolanaPriceAccount;
use solana_client::rpc_client::RpcClient;
use solana_program::pubkey::Pubkey;
use std::str::FromStr;
Expand All @@ -25,7 +25,7 @@ fn main() {
// get price data from key
let mut eth_price_account = clnt.get_account(&eth_price_key).unwrap();
let eth_price_feed =
load_price_feed_from_account(&eth_price_key, &mut eth_price_account).unwrap();
SolanaPriceAccount::account_to_feed(&eth_price_key, &mut eth_price_account).unwrap();

println!(".....ETH/USD.....");

Expand Down
4 changes: 3 additions & 1 deletion pyth-sdk-solana/examples/get_accounts.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ use pyth_sdk_solana::state::{
load_product_account,
CorpAction,
PriceType,
SolanaPriceAccount,
};
use solana_client::rpc_client::RpcClient;
use solana_program::pubkey::Pubkey;
Expand Down Expand Up @@ -62,7 +63,8 @@ fn main() {
let mut px_pkey = prod_acct.px_acc;
loop {
let price_data = clnt.get_account_data(&px_pkey).unwrap();
let price_account = load_price_account(&price_data).unwrap();
let price_account: &SolanaPriceAccount =
load_price_account(&price_data).unwrap();
let price_feed = price_account.to_price_feed(&px_pkey);

println!(" price_account .. {:?}", px_pkey);
Expand Down
41 changes: 32 additions & 9 deletions pyth-sdk-solana/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,11 @@ use solana_program::account_info::{
};
use solana_program::pubkey::Pubkey;

use state::load_price_account;
use state::{
load_price_account,
GenericPriceAccount,
SolanaPriceAccount,
};

pub use pyth_sdk::{
Price,
Expand All @@ -27,24 +31,43 @@ pub use pyth_sdk::{
pub const VALID_SLOT_PERIOD: u64 = 25;

/// Loads Pyth Feed Price from Price Account Info.
#[deprecated(note = "solana-specific, use SolanaPriceAccount::account_info_to_feed instead.")]
pub fn load_price_feed_from_account_info(
price_account_info: &AccountInfo,
) -> Result<PriceFeed, PythError> {
let data = price_account_info
.try_borrow_data()
.map_err(|_| PythError::InvalidAccountData)?;
let price_account = load_price_account(*data)?;

Ok(price_account.to_price_feed(price_account_info.key))
SolanaPriceAccount::account_info_to_feed(price_account_info)
}

/// Loads Pyth Price Feed from Account when using Solana Client.
///
/// It is a helper function which constructs Account Info when reading Account in clients.
#[deprecated(note = "solana-specific, use SolanaPriceAccount::account_to_feed instead.")]
pub fn load_price_feed_from_account(
price_key: &Pubkey,
price_account: &mut impl Account,
) -> Result<PriceFeed, PythError> {
let price_account_info = (price_key, price_account).into_account_info();
load_price_feed_from_account_info(&price_account_info)
SolanaPriceAccount::account_to_feed(price_key, price_account)
}

impl<const N: usize, T: 'static> GenericPriceAccount<N, T>
where
T: Default,
T: Copy,
{
pub fn account_info_to_feed(price_account_info: &AccountInfo) -> Result<PriceFeed, PythError> {
load_price_account::<N, T>(
*price_account_info
.try_borrow_data()
.map_err(|_| PythError::InvalidAccountData)?,
)
.map(|acc| acc.to_price_feed(price_account_info.key))
}

pub fn account_to_feed(
price_key: &Pubkey,
price_account: &mut impl Account,
) -> Result<PriceFeed, PythError> {
let price_account_info = (price_key, price_account).into_account_info();
Self::account_info_to_feed(&price_account_info)
}
}
Loading

0 comments on commit 096432f

Please sign in to comment.