use std::collections::HashMap;
use solana_pubkey::Pubkey;
use pyra_types::{Cache, KaminoObligation, KaminoReserve};
use crate::{RedisClient, RedisError, RedisKey, RedisResult};
impl RedisClient {
pub async fn fetch_kamino_obligation(
&self,
vault_address: &Pubkey,
lending_market: &Pubkey,
) -> RedisResult<Option<KaminoObligation>> {
let key = RedisKey::kamino_obligation(vault_address, lending_market);
let cached: Option<Cache<KaminoObligation>> = self.get_json(key.as_str()).await?;
Ok(cached.map(|c| c.account))
}
pub async fn fetch_kamino_obligation_by_pubkey(
&self,
obligation_pubkey: &Pubkey,
) -> RedisResult<Pubkey> {
let key = RedisKey::kamino_obligation_by_pubkey(obligation_pubkey);
let raw = self
.get(key.as_str())
.await?
.ok_or_else(|| RedisError::NotFound("Kamino obligation reverse mapping".into()))?;
raw.parse::<Pubkey>()
.map_err(|_| RedisError::NotFound("Invalid pubkey in obligation reverse mapping".into()))
}
pub async fn fetch_kamino_reserve(
&self,
reserve_pubkey: &Pubkey,
) -> RedisResult<Option<KaminoReserve>> {
let key = RedisKey::kamino_reserve(reserve_pubkey);
let cached: Option<Cache<KaminoReserve>> = self.get_json(key.as_str()).await?;
Ok(cached.map(|c| c.account))
}
pub async fn fetch_kamino_reserves(
&self,
pubkeys: &[Pubkey],
) -> RedisResult<HashMap<Pubkey, KaminoReserve>> {
if pubkeys.is_empty() {
return Ok(HashMap::new());
}
let keys: Vec<String> = pubkeys
.iter()
.map(|pk| RedisKey::kamino_reserve(pk).to_string())
.collect();
let values = self.mget(&keys).await?;
let mut result = HashMap::with_capacity(pubkeys.len());
for (pk, val) in pubkeys.iter().zip(values.into_iter()) {
if let Some(raw) = val {
if let Ok(cached) = serde_json::from_str::<Cache<KaminoReserve>>(&raw) {
result.insert(*pk, cached.account);
}
}
}
Ok(result)
}
pub async fn fetch_all_kamino_reserves(&self) -> RedisResult<HashMap<Pubkey, KaminoReserve>> {
let pattern = RedisKey::kamino_reserve_glob();
let keys = self.scan_keys(&pattern).await?;
if keys.is_empty() {
return Ok(HashMap::new());
}
let prefix_with_colon = format!("{}:", RedisKey::KAMINO_RESERVE_PREFIX);
let values = self.mget(&keys).await?;
let mut result = HashMap::with_capacity(keys.len());
for (key, val) in keys.iter().zip(values.into_iter()) {
if let Some(raw) = val {
if let Ok(cached) = serde_json::from_str::<Cache<KaminoReserve>>(&raw) {
if let Some(pk_str) = key.strip_prefix(prefix_with_colon.as_str()) {
if let Ok(pk) = pk_str.parse::<Pubkey>() {
result.insert(pk, cached.account);
}
}
}
}
}
Ok(result)
}
}