use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct Cursor {
pub block_number: u64,
pub block_hash: String,
pub confirmation_depth: u64,
}
impl Cursor {
pub fn new(block_number: u64, block_hash: impl Into<String>, confirmation_depth: u64) -> Self {
Self {
block_number,
block_hash: block_hash.into(),
confirmation_depth,
}
}
pub fn advance(&mut self, block_number: u64, block_hash: impl Into<String>) {
self.block_number = block_number;
self.block_hash = block_hash.into();
}
pub fn is_confirmed(&self, target: u64, head_number: u64) -> bool {
head_number.saturating_sub(target) >= self.confirmation_depth
}
pub fn next_block(&self) -> u64 {
self.block_number + 1
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn cursor_advance() {
let mut cursor = Cursor::new(100, "0xaaa", 12);
cursor.advance(101, "0xbbb");
assert_eq!(cursor.block_number, 101);
assert_eq!(cursor.block_hash, "0xbbb");
}
#[test]
fn cursor_confirmation_depth() {
let cursor = Cursor::new(100, "0xaaa", 12);
assert!(cursor.is_confirmed(100, 112)); assert!(!cursor.is_confirmed(100, 111)); }
#[test]
fn cursor_next_block() {
let cursor = Cursor::new(500, "0x123", 6);
assert_eq!(cursor.next_block(), 501);
}
}