x_http/
assertions.rs

1use serde_json::Value;
2
3pub fn json_values_match(actual: &Value, expected: &Value) -> bool {
4    match (actual, expected) {
5        (Value::String(a), Value::String(e)) => a == e,
6        (Value::Number(a), Value::Number(e)) => a == e,
7        (Value::Bool(a), Value::Bool(e)) => a == e,
8        (Value::Null, Value::Null) => true,
9        (Value::Array(a), Value::Array(e)) => {
10            a.len() == e.len() && a.iter().zip(e.iter()).all(|(a, e)| json_values_match(a, e))
11        }
12        (Value::Object(a), Value::Object(e)) => {
13            a.len() == e.len()
14                && a.iter()
15                    .all(|(k, v)| e.get(k).is_some_and(|ev| json_values_match(v, ev)))
16        }
17        _ => false,
18    }
19}
20
21pub fn matches_pattern(value: &str, pattern: &str) -> bool {
22    if pattern.contains('*') {
23        let parts: Vec<&str> = pattern.split('*').collect();
24        if parts.is_empty() {
25            return true;
26        }
27
28        let mut pos = 0;
29        for (i, part) in parts.iter().enumerate() {
30            if i == 0 && !part.is_empty() {
31                if !value.starts_with(part) {
32                    return false;
33                }
34                pos += part.len();
35            } else if i == parts.len() - 1 && !part.is_empty() {
36                if !value.ends_with(part) {
37                    return false;
38                }
39            } else if !part.is_empty() {
40                if let Some(found_pos) = value[pos..].find(part) {
41                    pos += found_pos + part.len();
42                } else {
43                    return false;
44                }
45            }
46        }
47        true
48    } else {
49        value == pattern
50    }
51}
52
53#[cfg(test)]
54mod tests {
55    use super::*;
56    use serde_json::json;
57
58    #[test]
59    fn test_json_values_match() {
60        assert!(json_values_match(&json!("test"), &json!("test")));
61        assert!(json_values_match(&json!(42), &json!(42)));
62        assert!(json_values_match(&json!(true), &json!(true)));
63        assert!(json_values_match(&json!(null), &json!(null)));
64        assert!(json_values_match(
65            &json!({"a": 1, "b": 2}),
66            &json!({"a": 1, "b": 2})
67        ));
68        assert!(json_values_match(&json!([1, 2, 3]), &json!([1, 2, 3])));
69
70        assert!(!json_values_match(&json!("test"), &json!("other")));
71        assert!(!json_values_match(&json!(42), &json!(43)));
72        assert!(!json_values_match(&json!(true), &json!(false)));
73    }
74
75    #[test]
76    fn test_matches_pattern() {
77        assert!(matches_pattern("hello world", "hello world"));
78        assert!(matches_pattern("hello world", "hello*"));
79        assert!(matches_pattern("hello world", "*world"));
80        assert!(matches_pattern("hello world", "*lo wo*"));
81        assert!(matches_pattern("hello world", "hello*world"));
82
83        assert!(!matches_pattern("hello world", "goodbye*"));
84        assert!(!matches_pattern("hello world", "*universe"));
85    }
86}