use ex3_serde::bincode::{deserialize, serialize};
use num_bigint::BigUint;

use ex3_node_error::OtherError;

use crate::{CanisterId, WalletRegisterId};

#[derive(Clone, Debug)]
pub struct SnapshotVault {
    pub canister_id: CanisterId,
    pub seq_id: u64,
    pub wallet_start_id: WalletRegisterId,
    pub max_wallet_count: BigUint,
}

impl SnapshotVault {
    pub fn encode(&self) -> Vec<u8> {
        serialize(&(
            &self.canister_id,
            &self.seq_id,
            &self.wallet_start_id,
            &self.max_wallet_count,
        ))
        .unwrap()
    }
}

impl TryFrom<&[u8]> for SnapshotVault {
    type Error = OtherError;

    fn try_from(value: &[u8]) -> Result<Self, Self::Error> {
        let (canister_id, seq_id, wallet_start_id, max_wallet_count) = deserialize(value)
            .map_err(|e| OtherError::new(format!("Failed to deserialize vault: {}", e)))?;
        Ok(SnapshotVault {
            canister_id,
            seq_id,
            wallet_start_id,
            max_wallet_count,
        })
    }
}

pub type BalanceVault = SnapshotVault;
pub type SecretVault = SnapshotVault;
pub type WalletRegistry = SnapshotVault;
