use std::sync::Arc;
use clockwork_client::{
network::state::{Pool, Registry, Snapshot, SnapshotFrame, Worker},
Client as ClockworkClient,
};
use log::info;
use solana_sdk::transaction::Transaction;
use crate::pool_position::PoolPosition;
pub fn build_pool_rotation_tx<'a>(
client: Arc<ClockworkClient>,
pool_position: PoolPosition,
registry: Registry,
snapshot: Snapshot,
snapshot_frame: SnapshotFrame,
worker_id: u64,
) -> Option<Transaction> {
info!("nonce: {:?} total_stake: {:?} current_position: {:?} stake_offset: {:?} stake_amount: {:?}",
registry.nonce.checked_rem(snapshot.total_stake),
snapshot.total_stake,
pool_position.current_position,
snapshot_frame.stake_offset,
snapshot_frame.stake_amount,
);
if registry.nonce == 0 {
return None;
}
if snapshot.total_stake == 0 {
return None;
}
if pool_position.current_position.is_some() {
return None;
}
if snapshot_frame.stake_amount.eq(&0) {
return None;
}
let is_rotation_window_open = match registry.nonce.checked_rem(snapshot.total_stake) {
None => false,
Some(sample) => {
sample >= snapshot_frame.stake_offset
&& sample
< snapshot_frame
.stake_offset
.checked_add(snapshot_frame.stake_amount)
.unwrap()
}
};
if !is_rotation_window_open {
return None;
}
let snapshot_pubkey = Snapshot::pubkey(snapshot.id);
let ix = clockwork_client::network::instruction::pool_rotate(
Pool::pubkey(0),
client.payer_pubkey(),
snapshot_pubkey,
SnapshotFrame::pubkey(snapshot_pubkey, worker_id),
Worker::pubkey(worker_id),
);
let mut tx = Transaction::new_with_payer(&[ix.clone()], Some(&client.payer_pubkey()));
tx.sign(&[client.payer()], client.get_latest_blockhash().unwrap());
return Some(tx);
}