kanidmd_lib/valueset/
uint32.rs
1use crate::prelude::*;
2use crate::schema::SchemaAttribute;
3use crate::valueset::{
4 DbValueSetV2, ScimResolveStatus, ValueSet, ValueSetResolveStatus, ValueSetScimPut,
5};
6use kanidm_proto::scim_v1::JsonValue;
7use smolset::SmolSet;
8
9#[derive(Debug, Clone)]
10pub struct ValueSetUint32 {
11 set: SmolSet<[u32; 1]>,
12}
13
14impl ValueSetUint32 {
15 pub fn new(b: u32) -> Box<Self> {
16 let mut set = SmolSet::new();
17 set.insert(b);
18 Box::new(ValueSetUint32 { set })
19 }
20
21 pub fn push(&mut self, b: u32) -> bool {
22 self.set.insert(b)
23 }
24
25 pub fn from_dbvs2(data: Vec<u32>) -> Result<ValueSet, OperationError> {
26 let set = data.into_iter().collect();
27 Ok(Box::new(ValueSetUint32 { set }))
28 }
29
30 #[allow(clippy::should_implement_trait)]
33 pub fn from_iter<T>(iter: T) -> Option<Box<Self>>
34 where
35 T: IntoIterator<Item = u32>,
36 {
37 let set = iter.into_iter().collect();
38 Some(Box::new(ValueSetUint32 { set }))
39 }
40}
41
42impl ValueSetScimPut for ValueSetUint32 {
43 fn from_scim_json_put(value: JsonValue) -> Result<ValueSetResolveStatus, OperationError> {
44 let value: u32 = serde_json::from_value(value).map_err(|err| {
45 error!(?err, "SCIM uint32 syntax invalid");
46 OperationError::SC0006Uint32SyntaxInvalid
47 })?;
48
49 let mut set = SmolSet::new();
50 set.insert(value);
51
52 Ok(ValueSetResolveStatus::Resolved(Box::new(ValueSetUint32 {
53 set,
54 })))
55 }
56}
57
58impl ValueSetT for ValueSetUint32 {
59 fn insert_checked(&mut self, value: Value) -> Result<bool, OperationError> {
60 match value {
61 Value::Uint32(u) => Ok(self.set.insert(u)),
62 _ => {
63 debug_assert!(false);
64 Err(OperationError::InvalidValueState)
65 }
66 }
67 }
68
69 fn clear(&mut self) {
70 self.set.clear();
71 }
72
73 fn remove(&mut self, pv: &PartialValue, _cid: &Cid) -> bool {
74 match pv {
75 PartialValue::Uint32(u) => self.set.remove(u),
76 _ => {
77 debug_assert!(false);
78 true
79 }
80 }
81 }
82
83 fn contains(&self, pv: &PartialValue) -> bool {
84 match pv {
85 PartialValue::Uint32(u) => self.set.contains(u),
86 _ => false,
87 }
88 }
89
90 fn substring(&self, _pv: &PartialValue) -> bool {
91 false
92 }
93
94 fn startswith(&self, _pv: &PartialValue) -> bool {
95 false
96 }
97
98 fn endswith(&self, _pv: &PartialValue) -> bool {
99 false
100 }
101
102 fn lessthan(&self, pv: &PartialValue) -> bool {
103 match pv {
104 PartialValue::Uint32(u) => self.set.iter().any(|i| i < u),
105 _ => false,
106 }
107 }
108
109 fn len(&self) -> usize {
110 self.set.len()
111 }
112
113 fn generate_idx_eq_keys(&self) -> Vec<String> {
114 self.set.iter().map(|b| b.to_string()).collect()
115 }
116
117 fn syntax(&self) -> SyntaxType {
118 SyntaxType::Uint32
119 }
120
121 fn validate(&self, _schema_attr: &SchemaAttribute) -> bool {
122 true
123 }
124
125 fn to_proto_string_clone_iter(&self) -> Box<dyn Iterator<Item = String> + '_> {
126 Box::new(self.set.iter().map(|b| b.to_string()))
127 }
128
129 fn to_scim_value(&self) -> Option<ScimResolveStatus> {
130 if self.len() == 1 {
131 let b = self.set.iter().copied().next().unwrap_or_default();
133 Some(b.into())
134 } else {
135 None
137 }
138 }
139
140 fn to_db_valueset_v2(&self) -> DbValueSetV2 {
141 DbValueSetV2::Uint32(self.set.iter().cloned().collect())
142 }
143
144 fn to_partialvalue_iter(&self) -> Box<dyn Iterator<Item = PartialValue> + '_> {
145 Box::new(self.set.iter().copied().map(PartialValue::new_uint32))
146 }
147
148 fn to_value_iter(&self) -> Box<dyn Iterator<Item = Value> + '_> {
149 Box::new(self.set.iter().copied().map(Value::new_uint32))
150 }
151
152 fn equal(&self, other: &ValueSet) -> bool {
153 if let Some(other) = other.as_uint32_set() {
154 &self.set == other
155 } else {
156 debug_assert!(false);
157 false
158 }
159 }
160
161 fn merge(&mut self, other: &ValueSet) -> Result<(), OperationError> {
162 if let Some(b) = other.as_uint32_set() {
163 mergesets!(self.set, b)
164 } else {
165 debug_assert!(false);
166 Err(OperationError::InvalidValueState)
167 }
168 }
169
170 fn to_uint32_single(&self) -> Option<u32> {
171 if self.set.len() == 1 {
172 self.set.iter().copied().take(1).next()
173 } else {
174 None
175 }
176 }
177
178 fn as_uint32_set(&self) -> Option<&SmolSet<[u32; 1]>> {
179 Some(&self.set)
180 }
181}
182
183#[cfg(test)]
184mod tests {
185 use super::ValueSetUint32;
186 use crate::prelude::*;
187
188 #[test]
189 fn test_valueset_basic() {
190 let mut vs = ValueSetUint32::new(0);
191 assert_eq!(vs.insert_checked(Value::new_uint32(0)), Ok(false));
192 assert_eq!(vs.insert_checked(Value::new_uint32(1)), Ok(true));
193 assert_eq!(vs.insert_checked(Value::new_uint32(1)), Ok(false));
194 }
195
196 #[test]
197 fn test_scim_uint32() {
198 let vs: ValueSet = ValueSetUint32::new(69);
199 crate::valueset::scim_json_reflexive(&vs, "69");
200
201 crate::valueset::scim_json_put_reflexive::<ValueSetUint32>(&vs, &[])
203 }
204}