use crate::hylo_stability_pool::client::{accounts, args};
use crate::hylo_stability_pool::events::StabilityPoolStats;
use crate::pda::SOL_USD_PYTH_FEED;
use crate::util::{simulation_config, ProgramClient};
use crate::{hylo_exchange, hylo_stability_pool, pda};
use std::rc::Rc;
use anchor_client::solana_sdk::signature::{Keypair, Signature};
use anchor_client::Program;
use anchor_lang::prelude::Pubkey;
use anchor_lang::AnchorDeserialize;
use anchor_spl::token;
use anyhow::{anyhow, Result};
use base64::prelude::{Engine, BASE64_STANDARD};
pub struct StabilityPoolClient {
program: Program<Rc<Keypair>>,
}
impl ProgramClient for StabilityPoolClient {
const PROGRAM_ID: Pubkey = hylo_stability_pool::ID;
fn build_client(program: Program<Rc<Keypair>>) -> StabilityPoolClient {
StabilityPoolClient { program }
}
}
impl StabilityPoolClient {
pub async fn rebalance_stable_to_lever(&self) -> Result<Signature> {
let accounts = accounts::RebalanceStableToLever {
payer: self.program.payer(),
pool_config: pda::pool_config(),
hylo: pda::hylo(),
stablecoin_mint: pda::hyusd(),
stablecoin_pool: pda::hyusd_pool(),
pool_auth: pda::pool_auth(),
levercoin_pool: pda::xsol_pool(),
fee_auth: pda::fee_auth(pda::hyusd()),
fee_vault: pda::fee_vault(pda::hyusd()),
levercoin_mint: pda::xsol(),
sol_usd_pyth_feed: SOL_USD_PYTH_FEED,
stablecoin_auth: pda::hyusd_auth(),
levercoin_auth: pda::xsol_auth(),
hylo_event_authority: pda::event_auth(hylo_exchange::ID),
hylo_exchange_program: hylo_exchange::ID,
token_program: token::ID,
event_authority: pda::event_auth(hylo_stability_pool::ID),
program: hylo_stability_pool::ID,
};
let args = args::RebalanceStableToLever {};
let sig = self
.program
.request()
.accounts(accounts)
.args(args)
.send()
.await?;
Ok(sig)
}
pub async fn rebalance_lever_to_stable(&self) -> Result<Signature> {
let accounts = accounts::RebalanceLeverToStable {
payer: self.program.payer(),
pool_config: pda::pool_config(),
hylo: pda::hylo(),
stablecoin_mint: pda::hyusd(),
stablecoin_pool: pda::hyusd_pool(),
pool_auth: pda::pool_auth(),
levercoin_pool: pda::xsol_pool(),
fee_auth: pda::fee_auth(pda::hyusd()),
fee_vault: pda::fee_vault(pda::hyusd()),
levercoin_mint: pda::xsol(),
sol_usd_pyth_feed: SOL_USD_PYTH_FEED,
stablecoin_auth: pda::hyusd_auth(),
levercoin_auth: pda::xsol_auth(),
hylo_event_authority: pda::event_auth(hylo_exchange::ID),
hylo_exchange_program: hylo_exchange::ID,
token_program: token::ID,
event_authority: pda::event_auth(hylo_stability_pool::ID),
program: hylo_stability_pool::ID,
};
let args = args::RebalanceLeverToStable {};
let sig = self
.program
.request()
.accounts(accounts)
.args(args)
.send()
.await?;
Ok(sig)
}
pub async fn simulate_get_stats(&self) -> Result<StabilityPoolStats> {
let accounts = accounts::GetStats {
pool_config: pda::pool_config(),
hylo: pda::hylo(),
stablecoin_mint: pda::hyusd(),
levercoin_mint: pda::xsol(),
pool_auth: pda::pool_auth(),
stablecoin_pool: pda::hyusd_pool(),
levercoin_pool: pda::xsol_pool(),
lp_token_mint: pda::shyusd(),
sol_usd_pyth_feed: SOL_USD_PYTH_FEED,
};
let args = args::GetStats {};
let tx = self
.program
.request()
.accounts(accounts)
.args(args)
.signed_transaction()
.await?;
let rpc = self.program.rpc();
let (data, _) = rpc
.simulate_transaction_with_config(&tx, simulation_config())
.await?
.value
.return_data
.ok_or(anyhow!("No return data for `get_stats`"))?
.data;
let bytes = BASE64_STANDARD.decode(data)?;
let stats = StabilityPoolStats::try_from_slice(&bytes)?;
Ok(stats)
}
}