cull_gmail/
retention.rs

1mod message_age;
2
3pub use message_age::MessageAge;
4
5/// Retention policy configuration for email messages.
6///
7/// A retention policy defines how old messages should be before they are subject
8/// to retention actions (trash/delete), and whether a label should be automatically
9/// generated to categorize messages matching this policy.
10///
11/// # Examples
12///
13/// ```
14/// use cull_gmail::{Retention, MessageAge};
15///
16/// // Create a retention policy for messages older than 6 months
17/// let policy = Retention::new(MessageAge::Months(6), true);
18///
19/// // Create a retention policy without auto-generated labels
20/// let policy = Retention::new(MessageAge::Years(1), false);
21/// ```
22#[derive(Debug, Clone, PartialEq, Eq, Hash)]
23pub struct Retention {
24    age: MessageAge,
25    generate_label: bool,
26}
27
28impl Default for Retention {
29    fn default() -> Self {
30        Self {
31            age: MessageAge::Years(5),
32            generate_label: true,
33        }
34    }
35}
36
37impl Retention {
38    /// Create a new retention policy.
39    ///
40    /// # Arguments
41    ///
42    /// * `age` - The message age threshold for this retention policy
43    /// * `generate_label` - Whether to automatically generate a label for messages matching this policy
44    ///
45    /// # Examples
46    ///
47    /// ```
48    /// use cull_gmail::{Retention, MessageAge};
49    ///
50    /// // Policy for messages older than 30 days with auto-generated label
51    /// let policy = Retention::new(MessageAge::Days(30), true);
52    ///
53    /// // Policy for messages older than 1 year without label generation
54    /// let policy = Retention::new(MessageAge::Years(1), false);
55    /// ```
56    pub fn new(age: MessageAge, generate_label: bool) -> Self {
57        Retention {
58            age,
59            generate_label,
60        }
61    }
62
63    /// Get the message age threshold for this retention policy.
64    ///
65    /// # Examples
66    ///
67    /// ```
68    /// use cull_gmail::{Retention, MessageAge};
69    ///
70    /// let policy = Retention::new(MessageAge::Days(30), true);
71    /// assert_eq!(policy.age(), &MessageAge::Days(30));
72    /// ```
73    #[must_use]
74    pub fn age(&self) -> &MessageAge {
75        &self.age
76    }
77
78    /// Check if this retention policy should generate automatic labels.
79    ///
80    /// When `true`, messages matching this retention policy will be automatically
81    /// tagged with a generated label based on the age specification.
82    ///
83    /// # Examples
84    ///
85    /// ```
86    /// use cull_gmail::{Retention, MessageAge};
87    ///
88    /// let policy = Retention::new(MessageAge::Days(30), true);
89    /// assert_eq!(policy.generate_label(), true);
90    ///
91    /// let policy = Retention::new(MessageAge::Days(30), false);
92    /// assert_eq!(policy.generate_label(), false);
93    /// ```
94    #[must_use]
95    pub fn generate_label(&self) -> bool {
96        self.generate_label
97    }
98
99    /// Set whether this retention policy should generate automatic labels.
100    ///
101    /// # Examples
102    ///
103    /// ```
104    /// use cull_gmail::{Retention, MessageAge};
105    ///
106    /// let mut policy = Retention::new(MessageAge::Days(30), false);
107    /// policy.set_generate_label(true);
108    /// assert_eq!(policy.generate_label(), true);
109    /// ```
110    pub fn set_generate_label(&mut self, generate_label: bool) {
111        self.generate_label = generate_label;
112    }
113}
114
115#[cfg(test)]
116mod tests {
117    use super::*;
118
119    #[test]
120    fn test_retention_new() {
121        let age = MessageAge::Days(30);
122        let retention = Retention::new(age.clone(), true);
123
124        assert_eq!(retention.age(), &age);
125        assert!(retention.generate_label());
126    }
127
128    #[test]
129    fn test_retention_new_no_label() {
130        let age = MessageAge::Years(1);
131        let retention = Retention::new(age.clone(), false);
132
133        assert_eq!(retention.age(), &age);
134        assert!(!retention.generate_label());
135    }
136
137    #[test]
138    fn test_retention_set_generate_label() {
139        let age = MessageAge::Months(6);
140        let mut retention = Retention::new(age.clone(), false);
141
142        assert!(!retention.generate_label());
143
144        retention.set_generate_label(true);
145        assert!(retention.generate_label());
146
147        retention.set_generate_label(false);
148        assert!(!retention.generate_label());
149    }
150
151    #[test]
152    fn test_retention_clone() {
153        let age = MessageAge::Weeks(2);
154        let original = Retention::new(age.clone(), true);
155        let cloned = original.clone();
156
157        assert_eq!(original, cloned);
158        assert_eq!(original.age(), cloned.age());
159        assert_eq!(original.generate_label(), cloned.generate_label());
160    }
161
162    #[test]
163    fn test_retention_equality() {
164        let age1 = MessageAge::Days(30);
165        let age2 = MessageAge::Days(30);
166        let age3 = MessageAge::Days(31);
167
168        let retention1 = Retention::new(age1, true);
169        let retention2 = Retention::new(age2, true);
170        let retention3 = Retention::new(age3, true);
171        let retention4 = Retention::new(MessageAge::Days(30), false);
172
173        assert_eq!(retention1, retention2);
174        assert_ne!(retention1, retention3); // different age
175        assert_ne!(retention1, retention4); // different generate_label
176    }
177
178    #[test]
179    fn test_retention_default() {
180        let default = Retention::default();
181
182        assert_eq!(default.age(), &MessageAge::Years(5));
183        assert!(default.generate_label());
184    }
185
186    #[test]
187    fn test_retention_with_different_age_types() {
188        let retention_days = Retention::new(MessageAge::Days(90), true);
189        let retention_weeks = Retention::new(MessageAge::Weeks(12), false);
190        let retention_months = Retention::new(MessageAge::Months(3), true);
191        let retention_years = Retention::new(MessageAge::Years(1), false);
192
193        assert_eq!(retention_days.age().period_type(), "days");
194        assert_eq!(retention_weeks.age().period_type(), "weeks");
195        assert_eq!(retention_months.age().period_type(), "months");
196        assert_eq!(retention_years.age().period_type(), "years");
197
198        assert!(retention_days.generate_label());
199        assert!(!retention_weeks.generate_label());
200        assert!(retention_months.generate_label());
201        assert!(!retention_years.generate_label());
202    }
203
204    #[test]
205    fn test_retention_debug() {
206        let retention = Retention::new(MessageAge::Days(30), true);
207        let debug_str = format!("{retention:?}");
208
209        assert!(debug_str.contains("Retention"));
210        assert!(debug_str.contains("Days(30)"));
211        assert!(debug_str.contains("true"));
212    }
213}