use crate::error::TripError;
use std::fmt::Debug;
#[derive(Debug)]
pub enum OnceFuse<T> {
#[allow(private_interfaces)]
State(FuseState<T>),
}
#[derive(Debug)]
enum FuseState<T> {
Armed(T),
Burnt,
ExplicitBurnt,
}
impl<T: 'static> OnceFuse<T> {
#[inline]
pub fn new(oto: T) -> Self
where
T:
{
Self::State(FuseState::Armed(oto))
}
#[must_use = "This returns the inner value or an error. Handle the result appropriately."]
pub fn try_use(&mut self) -> Result<T, TripError> {
let current = std::mem::replace(self, Self::State(FuseState::Burnt));
match current {
Self::State(FuseState::Armed(value)) => Ok(value),
Self::State(FuseState::Burnt) => Err(TripError::FuseBurntAfterUsage),
Self::State(FuseState::ExplicitBurnt) => Err(TripError::FuseBurntExplicitly),
}
}
pub fn burn_it(&mut self) -> bool {
if let Self::State(FuseState::Armed(_)) = self {
let _ = std::mem::replace(self, OnceFuse::State(FuseState::ExplicitBurnt));
true
} else {
false
}
}
pub fn is_armed(&self) -> bool {
matches!(self, OnceFuse::State(FuseState::Armed(_)))
}
pub fn is_burnt(&self) -> bool {
!self.is_armed()
}
}