vessel/
lib.rs

1use std::collections::BTreeMap;
2
3#[derive(Default, Clone, Debug)]
4pub struct Vessel {
5    value_bag: BTreeMap<String, String>,
6}
7
8impl Vessel {
9    pub fn new() -> Self {
10        Self {
11            value_bag: BTreeMap::default(),
12        }
13    }
14
15    pub fn with_value(&self, key: &str, value: &str) -> Self {
16        let mut value_bag = self.value_bag.clone();
17
18        value_bag.insert(key.into(), value.into());
19
20        Self { value_bag }
21    }
22
23    pub fn get_value(&self, key: &str) -> Option<&String> {
24        self.value_bag.get(key)
25    }
26
27    pub fn get_values(&self) -> &BTreeMap<String, String> {
28        &self.value_bag
29    }
30}
31
32#[cfg(test)]
33mod test {
34    use std::collections::BTreeMap;
35
36    use crate::Vessel;
37
38    #[test]
39    fn can_add_value() {
40        let vessel = Vessel::default();
41
42        let new_vessel = vessel.with_value("some-key", "some-value");
43
44        assert_eq!(
45            &BTreeMap::from([("some-key".into(), "some-value".into())]),
46            new_vessel.get_values()
47        )
48    }
49    #[test]
50    fn is_immutable() {
51        let vessel = Vessel::default();
52
53        let new_vessel = vessel.with_value("some-key", "some-value");
54
55        assert_ne!(vessel.get_values(), new_vessel.get_values())
56    }
57
58    #[test]
59    fn get_value() {
60        let vessel = Vessel::default();
61
62        let new_vessel = vessel.with_value("some-key", "some-value");
63
64        assert_eq!(
65            Some(&"some-value".to_string()),
66            new_vessel.get_value("some-key")
67        )
68    }
69    #[test]
70    fn value_not_found() {
71        let vessel = Vessel::default();
72
73        let new_vessel = vessel.with_value("some-key", "some-value");
74
75        assert_eq!(None, new_vessel.get_value("bogus"))
76    }
77}