1use std::collections::HashMap;
5
6use buffa::bytes::Bytes;
7
8use crate::{
9 dynamic::message::DynamicMessage,
10 field::{FieldDescriptor, Kind},
11};
12
13#[derive(Clone, Debug, PartialEq)]
20pub enum Value {
21 Bool(bool),
23 I32(i32),
25 I64(i64),
27 U32(u32),
29 U64(u64),
31 F32(f32),
33 F64(f64),
35 String(String),
37 Bytes(Bytes),
39 EnumNumber(i32),
45 Message(DynamicMessage),
47 List(Vec<Value>),
50 Map(HashMap<MapKey, Value>),
52}
53
54#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
59pub enum MapKey {
60 Bool(bool),
62 I32(i32),
64 I64(i64),
66 U32(u32),
68 U64(u64),
70 String(String),
72}
73
74#[derive(Clone, Debug, PartialEq, thiserror::Error)]
76pub enum SetFieldError {
77 #[error("field not found")]
79 NotFound,
80 #[error("invalid value for field `{}`", field.full_name())]
82 InvalidType {
83 field: FieldDescriptor,
85 value: Box<Value>,
87 },
88}
89
90impl Value {
91 #[must_use]
96 pub fn default_value(kind: &Kind) -> Self {
97 match kind {
98 Kind::Bool => Value::Bool(false),
99 Kind::Int32 | Kind::Sint32 | Kind::Sfixed32 => Value::I32(0),
100 Kind::Int64 | Kind::Sint64 | Kind::Sfixed64 => Value::I64(0),
101 Kind::Uint32 | Kind::Fixed32 => Value::U32(0),
102 Kind::Uint64 | Kind::Fixed64 => Value::U64(0),
103 Kind::Float => Value::F32(0.0),
104 Kind::Double => Value::F64(0.0),
105 Kind::String => Value::String(String::new()),
106 Kind::Bytes => Value::Bytes(Bytes::new()),
107 Kind::Enum(_) => Value::EnumNumber(0),
108 Kind::Message(m) => Value::Message(DynamicMessage::new(m.clone())),
109 }
110 }
111
112 #[must_use]
119 pub fn default_value_for_field(field: &FieldDescriptor) -> Self {
120 if field.is_list() {
121 return Value::List(Vec::new());
122 }
123 if field.is_map() {
124 return Value::Map(HashMap::new());
125 }
126 if let Some(value) = field.parsed_default_value() {
127 return value;
128 }
129 Value::default_value(&field.kind())
130 }
131
132 #[must_use]
137 pub fn is_default(&self, kind: &Kind) -> bool {
138 match (self, kind) {
139 (Value::Bool(b), Kind::Bool) => !*b,
140 (Value::I32(v), Kind::Int32 | Kind::Sint32 | Kind::Sfixed32) => *v == 0,
141 (Value::I64(v), Kind::Int64 | Kind::Sint64 | Kind::Sfixed64) => *v == 0,
142 (Value::U32(v), Kind::Uint32 | Kind::Fixed32) => *v == 0,
143 (Value::U64(v), Kind::Uint64 | Kind::Fixed64) => *v == 0,
144 (Value::F32(v), Kind::Float) => *v == 0.0,
145 (Value::F64(v), Kind::Double) => *v == 0.0,
146 (Value::String(s), Kind::String) => s.is_empty(),
147 (Value::Bytes(b), Kind::Bytes) => b.is_empty(),
148 (Value::EnumNumber(n), Kind::Enum(_)) => *n == 0,
149 (Value::Message(m), Kind::Message(_)) => m.is_empty(),
150 (Value::List(l), _) => l.is_empty(),
151 (Value::Map(m), _) => m.is_empty(),
152 _ => false,
153 }
154 }
155
156 #[must_use]
163 pub fn is_valid_for_field(&self, field: &FieldDescriptor) -> bool {
164 if field.is_list() {
165 if let Value::List(items) = self {
166 let kind = field.kind();
167 return items.iter().all(|v| value_matches_kind(v, &kind));
168 }
169 return false;
170 }
171 if field.is_map() {
172 if let Value::Map(entries) = self {
173 let (key_kind, value_kind) = match map_entry_kinds(field) {
174 Some(kinds) => kinds,
175 None => return false,
176 };
177 return entries.iter().all(|(k, v)| {
178 map_key_matches_kind(k, &key_kind) && value_matches_kind(v, &value_kind)
179 });
180 }
181 return false;
182 }
183 value_matches_kind(self, &field.kind())
184 }
185
186 #[must_use]
190 pub fn as_bool(&self) -> Option<bool> {
191 match self {
192 Value::Bool(v) => Some(*v),
193 _ => None,
194 }
195 }
196 #[must_use]
198 pub fn as_i32(&self) -> Option<i32> {
199 match self {
200 Value::I32(v) => Some(*v),
201 _ => None,
202 }
203 }
204 #[must_use]
206 pub fn as_i64(&self) -> Option<i64> {
207 match self {
208 Value::I64(v) => Some(*v),
209 _ => None,
210 }
211 }
212 #[must_use]
214 pub fn as_u32(&self) -> Option<u32> {
215 match self {
216 Value::U32(v) => Some(*v),
217 _ => None,
218 }
219 }
220 #[must_use]
222 pub fn as_u64(&self) -> Option<u64> {
223 match self {
224 Value::U64(v) => Some(*v),
225 _ => None,
226 }
227 }
228 #[must_use]
230 pub fn as_f32(&self) -> Option<f32> {
231 match self {
232 Value::F32(v) => Some(*v),
233 _ => None,
234 }
235 }
236 #[must_use]
238 pub fn as_f64(&self) -> Option<f64> {
239 match self {
240 Value::F64(v) => Some(*v),
241 _ => None,
242 }
243 }
244 #[must_use]
246 pub fn as_str(&self) -> Option<&str> {
247 match self {
248 Value::String(v) => Some(v.as_str()),
249 _ => None,
250 }
251 }
252 #[must_use]
254 pub fn as_bytes(&self) -> Option<&Bytes> {
255 match self {
256 Value::Bytes(v) => Some(v),
257 _ => None,
258 }
259 }
260 #[must_use]
262 pub fn as_enum_number(&self) -> Option<i32> {
263 match self {
264 Value::EnumNumber(v) => Some(*v),
265 _ => None,
266 }
267 }
268 #[must_use]
270 pub fn as_message(&self) -> Option<&DynamicMessage> {
271 match self {
272 Value::Message(v) => Some(v),
273 _ => None,
274 }
275 }
276 pub fn as_message_mut(&mut self) -> Option<&mut DynamicMessage> {
278 match self {
279 Value::Message(v) => Some(v),
280 _ => None,
281 }
282 }
283 #[must_use]
285 pub fn as_list(&self) -> Option<&[Value]> {
286 match self {
287 Value::List(v) => Some(v.as_slice()),
288 _ => None,
289 }
290 }
291 pub fn as_list_mut(&mut self) -> Option<&mut Vec<Value>> {
293 match self {
294 Value::List(v) => Some(v),
295 _ => None,
296 }
297 }
298 #[must_use]
300 pub fn as_map(&self) -> Option<&HashMap<MapKey, Value>> {
301 match self {
302 Value::Map(v) => Some(v),
303 _ => None,
304 }
305 }
306 pub fn as_map_mut(&mut self) -> Option<&mut HashMap<MapKey, Value>> {
308 match self {
309 Value::Map(v) => Some(v),
310 _ => None,
311 }
312 }
313}
314
315impl MapKey {
316 #[must_use]
325 pub fn default_value(kind: &Kind) -> Self {
326 match kind {
327 Kind::Bool => MapKey::Bool(false),
328 Kind::Int32 | Kind::Sint32 | Kind::Sfixed32 => MapKey::I32(0),
329 Kind::Int64 | Kind::Sint64 | Kind::Sfixed64 => MapKey::I64(0),
330 Kind::Uint32 | Kind::Fixed32 => MapKey::U32(0),
331 Kind::Uint64 | Kind::Fixed64 => MapKey::U64(0),
332 Kind::String => MapKey::String(String::new()),
333 other => panic!("invalid map-key kind: {other:?}"),
334 }
335 }
336}
337
338pub(crate) fn value_matches_kind(value: &Value, kind: &Kind) -> bool {
340 match (value, kind) {
341 (Value::Bool(_), Kind::Bool) => true,
342 (Value::I32(_), Kind::Int32 | Kind::Sint32 | Kind::Sfixed32) => true,
343 (Value::I64(_), Kind::Int64 | Kind::Sint64 | Kind::Sfixed64) => true,
344 (Value::U32(_), Kind::Uint32 | Kind::Fixed32) => true,
345 (Value::U64(_), Kind::Uint64 | Kind::Fixed64) => true,
346 (Value::F32(_), Kind::Float) => true,
347 (Value::F64(_), Kind::Double) => true,
348 (Value::String(_), Kind::String) => true,
349 (Value::Bytes(_), Kind::Bytes) => true,
350 (Value::EnumNumber(_), Kind::Enum(_)) => true,
351 (Value::Message(m), Kind::Message(d)) => m.descriptor().full_name() == d.full_name(),
355 _ => false,
356 }
357}
358
359pub(crate) fn map_key_matches_kind(key: &MapKey, kind: &Kind) -> bool {
360 matches!(
361 (key, kind),
362 (MapKey::Bool(_), Kind::Bool)
363 | (MapKey::I32(_), Kind::Int32 | Kind::Sint32 | Kind::Sfixed32)
364 | (MapKey::I64(_), Kind::Int64 | Kind::Sint64 | Kind::Sfixed64)
365 | (MapKey::U32(_), Kind::Uint32 | Kind::Fixed32)
366 | (MapKey::U64(_), Kind::Uint64 | Kind::Fixed64)
367 | (MapKey::String(_), Kind::String)
368 )
369}
370
371pub(crate) fn map_entry_kinds(field: &FieldDescriptor) -> Option<(Kind, Kind)> {
374 let Kind::Message(entry) = field.kind() else {
375 return None;
376 };
377 if !entry.is_map_entry() {
378 return None;
379 }
380 let key = entry.get_field_by_number(1)?.kind();
381 let value = entry.get_field_by_number(2)?.kind();
382 Some((key, value))
383}
384
385impl From<bool> for Value {
387 fn from(v: bool) -> Self {
388 Value::Bool(v)
389 }
390}
391impl From<i32> for Value {
392 fn from(v: i32) -> Self {
393 Value::I32(v)
394 }
395}
396impl From<i64> for Value {
397 fn from(v: i64) -> Self {
398 Value::I64(v)
399 }
400}
401impl From<u32> for Value {
402 fn from(v: u32) -> Self {
403 Value::U32(v)
404 }
405}
406impl From<u64> for Value {
407 fn from(v: u64) -> Self {
408 Value::U64(v)
409 }
410}
411impl From<f32> for Value {
412 fn from(v: f32) -> Self {
413 Value::F32(v)
414 }
415}
416impl From<f64> for Value {
417 fn from(v: f64) -> Self {
418 Value::F64(v)
419 }
420}
421impl From<String> for Value {
422 fn from(v: String) -> Self {
423 Value::String(v)
424 }
425}
426impl From<&str> for Value {
427 fn from(v: &str) -> Self {
428 Value::String(v.to_owned())
429 }
430}
431impl From<Bytes> for Value {
432 fn from(v: Bytes) -> Self {
433 Value::Bytes(v)
434 }
435}
436impl From<Vec<u8>> for Value {
437 fn from(v: Vec<u8>) -> Self {
438 Value::Bytes(Bytes::from(v))
439 }
440}
441impl From<DynamicMessage> for Value {
442 fn from(v: DynamicMessage) -> Self {
443 Value::Message(v)
444 }
445}