klend_interface/helpers/
refresh.rs1use solana_instruction::Instruction;
2use solana_pubkey::Pubkey;
3
4use super::{
5 common::{build_refresh_obligation, build_refresh_reserve},
6 info::{ObligationInfo, ReserveInfo},
7};
8use crate::{util::writable, KLEND_PROGRAM_ID};
9
10pub fn refresh_reserve(reserve: &ReserveInfo) -> Instruction {
14 build_refresh_reserve(reserve)
15}
16
17pub fn refresh_obligation(lending_market: &Pubkey, obligation: &ObligationInfo) -> Instruction {
23 build_refresh_obligation(lending_market, obligation)
24}
25
26pub fn refresh_reserves_batch(reserves: &[ReserveInfo], skip_price_updates: bool) -> Instruction {
34 let mut remaining = Vec::with_capacity(reserves.len() * 6);
35 for r in reserves {
36 remaining.push(writable(r.address));
37 remaining.push(crate::util::readonly(r.lending_market));
38 remaining.push(crate::util::optional_account(
39 &KLEND_PROGRAM_ID,
40 r.pyth_oracle,
41 false,
42 ));
43 remaining.push(crate::util::optional_account(
44 &KLEND_PROGRAM_ID,
45 r.switchboard_price_oracle,
46 false,
47 ));
48 remaining.push(crate::util::optional_account(
49 &KLEND_PROGRAM_ID,
50 r.switchboard_twap_oracle,
51 false,
52 ));
53 remaining.push(crate::util::optional_account(
54 &KLEND_PROGRAM_ID,
55 r.scope_prices,
56 false,
57 ));
58 }
59 crate::instructions::refresh::refresh_reserves_batch(skip_price_updates, remaining)
60}
61
62pub fn refresh_all_for_obligation(
79 lending_market: &Pubkey,
80 obligation: &ObligationInfo,
81 reserve_infos: &dyn Fn(&Pubkey) -> Option<ReserveInfo>,
82) -> Result<Vec<Instruction>, RefreshError> {
83 let mut seen =
85 Vec::with_capacity(obligation.deposit_reserves.len() + obligation.borrow_reserves.len());
86 let mut ixs = Vec::new();
87
88 for r in obligation
89 .deposit_reserves
90 .iter()
91 .chain(obligation.borrow_reserves.iter())
92 {
93 if !seen.contains(r) {
94 seen.push(*r);
95 let info = reserve_infos(r).ok_or(RefreshError::ReserveNotFound(*r))?;
96 ixs.push(build_refresh_reserve(&info));
97 }
98 }
99
100 ixs.push(build_refresh_obligation(lending_market, obligation));
101 Ok(ixs)
102}
103
104#[derive(Debug, Clone, PartialEq, Eq)]
106pub enum RefreshError {
107 ReserveNotFound(Pubkey),
109}
110
111impl std::fmt::Display for RefreshError {
112 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
113 match self {
114 RefreshError::ReserveNotFound(key) => {
115 write!(f, "reserve not found: {key}")
116 }
117 }
118 }
119}
120
121impl std::error::Error for RefreshError {}