use std::sync::Arc;
#[cfg(feature = "serde")]
use serde::{
Deserialize,
Deserializer,
};
#[cfg(feature = "serde")]
use crate::validation::validate_stage;
#[cfg_attr(feature = "serde", derive(serde::Serialize))]
#[derive(Clone, Debug, Eq, PartialEq)]
pub struct Stage {
pub(crate) id: Arc<str>,
pub(crate) name: Arc<str>,
pub(crate) position: Option<u64>,
pub(crate) total: Option<u64>,
}
#[cfg(feature = "serde")]
#[derive(Deserialize)]
struct StageWire {
id: Arc<str>,
name: Arc<str>,
position: Option<u64>,
total: Option<u64>,
}
#[cfg(feature = "serde")]
impl<'de> Deserialize<'de> for Stage {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: Deserializer<'de>,
{
let wire = StageWire::deserialize(deserializer)?;
let stage = Self {
id: wire.id,
name: wire.name,
position: wire.position,
total: wire.total,
};
validate_stage(&stage).map_err(serde::de::Error::custom)?;
Ok(stage)
}
}
impl Stage {
#[must_use]
pub fn new(id: &str, name: &str) -> Self {
Self {
id: Arc::from(id),
name: Arc::from(name),
position: None,
total: None,
}
}
#[must_use]
pub const fn position(mut self, position: u64, total: u64) -> Self {
self.position = Some(position);
self.total = Some(total);
self
}
#[must_use]
pub fn id(&self) -> &str {
&self.id
}
#[must_use]
pub fn name(&self) -> &str {
&self.name
}
#[must_use]
pub const fn position_value(&self) -> Option<u64> {
self.position
}
#[must_use]
pub const fn total(&self) -> Option<u64> {
self.total
}
}