Skip to main content

camel_api/
loop_eip.rs

1use std::sync::Arc;
2
3use crate::filter::FilterPredicate;
4
5/// How the loop terminates.
6#[derive(Clone)]
7pub enum LoopMode {
8    /// Fixed iteration count.
9    Count(usize),
10    /// While a runtime predicate evaluates to true.
11    While(FilterPredicate),
12}
13
14impl std::fmt::Debug for LoopMode {
15    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
16        match self {
17            LoopMode::Count(n) => write!(f, "Count({n})"),
18            LoopMode::While(_) => write!(f, "While(<predicate>)"),
19        }
20    }
21}
22
23#[derive(Clone, Debug)]
24pub struct LoopConfig {
25    pub mode: LoopMode,
26}
27
28impl LoopConfig {
29    pub fn new(mode: LoopMode) -> Self {
30        Self { mode }
31    }
32
33    pub fn mode_name(&self) -> &'static str {
34        match &self.mode {
35            LoopMode::Count(_) => "count",
36            LoopMode::While(_) => "while",
37        }
38    }
39}
40
41/// Maximum iterations for while-mode loops. Prevents infinite loops.
42pub const MAX_LOOP_ITERATIONS: usize = 10_000;
43
44#[cfg(test)]
45mod tests {
46    use super::*;
47
48    fn always_true() -> FilterPredicate {
49        Arc::new(|_| true)
50    }
51
52    #[test]
53    fn loop_config_new_count() {
54        let cfg = LoopConfig::new(LoopMode::Count(5));
55        assert_eq!(cfg.mode_name(), "count");
56    }
57
58    #[test]
59    fn loop_config_new_while() {
60        let cfg = LoopConfig::new(LoopMode::While(always_true()));
61        assert_eq!(cfg.mode_name(), "while");
62    }
63
64    #[test]
65    fn loop_mode_debug_count() {
66        let mode = LoopMode::Count(3);
67        assert_eq!(format!("{mode:?}"), "Count(3)");
68    }
69
70    #[test]
71    fn loop_mode_debug_while() {
72        let mode = LoopMode::While(always_true());
73        assert_eq!(format!("{mode:?}"), "While(<predicate>)");
74    }
75
76    #[test]
77    fn loop_mode_clone_count() {
78        let mode = LoopMode::Count(10);
79        let cloned = mode.clone();
80        assert_eq!(format!("{cloned:?}"), "Count(10)");
81    }
82
83    #[test]
84    fn loop_config_clone() {
85        let cfg = LoopConfig::new(LoopMode::Count(2));
86        let cloned = cfg.clone();
87        assert_eq!(cloned.mode_name(), "count");
88    }
89
90    #[test]
91    fn max_loop_iterations_value() {
92        assert_eq!(MAX_LOOP_ITERATIONS, 10_000);
93    }
94}