#[derive(Debug, Clone, Copy, PartialEq, Eq)]
#[non_exhaustive]
pub struct OwnershipSnapshot {
pub configured_limit: Option<usize>,
pub effective_limit: Option<usize>,
pub available: Option<usize>,
pub waiters: usize,
pub admission_open: bool,
pub cleanup_queued: usize,
pub cleanup_running: usize,
}
impl OwnershipSnapshot {
pub(crate) const fn new(
configured_limit: Option<usize>,
effective_limit: Option<usize>,
available: Option<usize>,
waiters: usize,
admission_open: bool,
cleanup_queued: usize,
cleanup_running: usize,
) -> Self {
Self {
configured_limit,
effective_limit,
available,
waiters,
admission_open,
cleanup_queued,
cleanup_running,
}
}
#[must_use]
pub fn retired(&self) -> Option<usize> {
self.configured_limit
.zip(self.effective_limit)
.map(|(configured, effective)| configured.saturating_sub(effective))
}
#[must_use]
pub fn in_use(&self) -> Option<usize> {
self.effective_limit
.zip(self.available)
.map(|(effective, available)| effective.saturating_sub(available))
}
}
#[cfg(test)]
mod tests {
use super::OwnershipSnapshot;
#[test]
fn finite_derived_counts_separate_retired_and_in_use_units() {
let snapshot = OwnershipSnapshot::new(Some(10), Some(8), Some(3), 2, true, 1, 2);
assert_eq!(snapshot.retired(), Some(2));
assert_eq!(snapshot.in_use(), Some(5));
}
#[test]
fn unlimited_derived_counts_have_no_finite_meaning() {
let snapshot = OwnershipSnapshot::new(None, None, None, 0, true, 4, 2);
assert_eq!(snapshot.retired(), None);
assert_eq!(snapshot.in_use(), None);
assert_eq!(snapshot.cleanup_queued, 4);
assert_eq!(snapshot.cleanup_running, 2);
}
}