use std::sync::{Arc, RwLock};
#[derive(Clone, Debug)]
pub struct CertState {
pub domains: Vec<String>,
pub expiry_ts: i64,
pub next_renewal_ts: i64,
}
pub type SharedCertState = Arc<RwLock<Vec<CertState>>>;
pub fn new_shared() -> SharedCertState {
Arc::new(RwLock::new(Vec::new()))
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn arc_clone_shares_state() {
let shared = new_shared();
{
let mut v = shared.write().unwrap();
v.push(CertState {
domains: vec!["example.com".into()],
expiry_ts: 9_999_999_999,
next_renewal_ts: 9_997_406_399,
});
}
let cloned = shared.clone();
assert_eq!(shared.read().unwrap().len(), cloned.read().unwrap().len(),);
}
#[test]
fn cert_state_clone_is_value_copy() {
let cs = CertState {
domains: vec!["a.com".into()],
expiry_ts: 1_000,
next_renewal_ts: 900,
};
let mut copy = cs.clone();
copy.expiry_ts = 2_000;
assert_eq!(cs.expiry_ts, 1_000);
}
#[test]
fn publish_and_read_back() {
let shared = new_shared();
{
let mut v = shared.write().unwrap();
v.push(CertState {
domains: vec!["one.example".into()],
expiry_ts: 1_000,
next_renewal_ts: 900,
});
}
let snapshot: Vec<CertState> = shared.read().unwrap().clone();
assert_eq!(snapshot.len(), 1);
assert_eq!(snapshot[0].domains, vec!["one.example".to_string()]);
assert_eq!(snapshot[0].expiry_ts, 1_000);
{
let mut v = shared.write().unwrap();
v[0].expiry_ts = 9_999;
v[0].next_renewal_ts = 9_899;
}
let after: Vec<CertState> = shared.read().unwrap().clone();
assert_eq!(after[0].expiry_ts, 9_999);
assert_eq!(after[0].next_renewal_ts, 9_899);
}
#[test]
fn new_shared_starts_empty() {
let shared = new_shared();
assert_eq!(shared.read().unwrap().len(), 0);
}
}