rustapi_core/
path_params.rs1use std::collections::HashMap;
4
5#[derive(Debug, Clone, Default)]
7pub struct PathParams {
8 inner: Vec<(String, String)>,
9}
10
11impl PathParams {
12 #[inline]
14 pub fn new() -> Self {
15 Self { inner: Vec::new() }
16 }
17
18 #[inline]
20 pub fn with_capacity(capacity: usize) -> Self {
21 Self {
22 inner: Vec::with_capacity(capacity),
23 }
24 }
25
26 #[inline]
28 pub fn insert(&mut self, key: String, value: String) {
29 self.inner.push((key, value));
30 }
31
32 #[inline]
34 pub fn get(&self, key: &str) -> Option<&String> {
35 self.inner.iter().find(|(k, _)| k == key).map(|(_, v)| v)
36 }
37
38 #[inline]
40 pub fn contains_key(&self, key: &str) -> bool {
41 self.inner.iter().any(|(k, _)| k == key)
42 }
43
44 #[inline]
46 pub fn is_empty(&self) -> bool {
47 self.inner.is_empty()
48 }
49
50 #[inline]
52 pub fn len(&self) -> usize {
53 self.inner.len()
54 }
55
56 #[inline]
58 pub fn iter(&self) -> impl Iterator<Item = (&String, &String)> {
59 self.inner.iter().map(|(k, v)| (k, v))
60 }
61
62 pub fn to_hashmap(&self) -> HashMap<String, String> {
64 self.inner.iter().cloned().collect()
65 }
66}
67
68impl FromIterator<(String, String)> for PathParams {
69 fn from_iter<I: IntoIterator<Item = (String, String)>>(iter: I) -> Self {
70 Self {
71 inner: iter.into_iter().collect(),
72 }
73 }
74}
75
76impl<'a> FromIterator<(&'a str, &'a str)> for PathParams {
77 fn from_iter<I: IntoIterator<Item = (&'a str, &'a str)>>(iter: I) -> Self {
78 Self {
79 inner: iter
80 .into_iter()
81 .map(|(k, v)| (k.to_string(), v.to_string()))
82 .collect(),
83 }
84 }
85}
86
87impl From<HashMap<String, String>> for PathParams {
88 fn from(map: HashMap<String, String>) -> Self {
89 Self {
90 inner: map.into_iter().collect(),
91 }
92 }
93}
94
95impl From<PathParams> for HashMap<String, String> {
96 fn from(params: PathParams) -> Self {
97 params.inner.into_iter().collect()
98 }
99}
100
101impl<'a> IntoIterator for &'a PathParams {
102 type Item = &'a (String, String);
103 type IntoIter = std::slice::Iter<'a, (String, String)>;
104
105 fn into_iter(self) -> Self::IntoIter {
106 self.inner.iter()
107 }
108}
109
110#[cfg(test)]
111mod tests {
112 use super::*;
113
114 #[test]
115 fn test_small_params() {
116 let mut params = PathParams::new();
117 params.insert("id".to_string(), "123".to_string());
118 params.insert("name".to_string(), "test".to_string());
119
120 assert_eq!(params.get("id"), Some(&"123".to_string()));
121 assert_eq!(params.get("name"), Some(&"test".to_string()));
122 assert_eq!(params.len(), 2);
123 }
124
125 #[test]
126 fn test_many_params() {
127 let mut params = PathParams::new();
128 for i in 0..10 {
129 params.insert(format!("key{}", i), format!("value{}", i));
130 }
131
132 assert_eq!(params.len(), 10);
133 }
134
135 #[test]
136 fn test_from_iterator() {
137 let params: PathParams = [("a", "1"), ("b", "2"), ("c", "3")].into_iter().collect();
138
139 assert_eq!(params.get("a"), Some(&"1".to_string()));
140 assert_eq!(params.get("b"), Some(&"2".to_string()));
141 assert_eq!(params.get("c"), Some(&"3".to_string()));
142 }
143
144 #[test]
145 fn test_to_hashmap_conversion() {
146 let mut params = PathParams::new();
147 params.insert("id".to_string(), "42".to_string());
148
149 let map = params.to_hashmap();
150 assert_eq!(map.get("id"), Some(&"42".to_string()));
151 }
152}