webwire_cli/schema/
struct.rs1use std::collections::HashMap;
2
3use crate::common::FilePosition;
4use crate::idl;
5
6use super::errors::ValidationError;
7use super::fqtn::FQTN;
8use super::namespace::Namespace;
9use super::r#type::Type;
10use super::typemap::TypeMap;
11
12pub struct Struct {
13 pub fqtn: FQTN,
14 pub generics: Vec<String>,
15 pub fields: Vec<Field>,
16 pub position: FilePosition,
17}
18
19#[derive(Clone)]
20pub struct Field {
21 pub name: String,
22 pub type_: Type,
23 pub optional: bool,
24 pub length: (Option<i64>, Option<i64>),
26 pub format: Option<String>,
27 pub position: FilePosition,
28}
29
30impl Struct {
31 pub(crate) fn from_idl(
32 istruct: &idl::Struct,
33 ns: &Namespace,
34 builtin_types: &HashMap<String, String>,
35 ) -> Self {
36 let fields = istruct
37 .fields
38 .iter()
39 .map(|ifield| Field::from_idl(ifield, ns, &builtin_types))
40 .collect();
41 Self {
42 fqtn: FQTN::new(&istruct.name, ns),
43 generics: istruct.generics.clone(),
44 fields,
45 position: istruct.position.clone(),
46 }
47 }
48 pub(crate) fn resolve(&mut self, type_map: &TypeMap) -> Result<(), ValidationError> {
49 for field in self.fields.iter_mut() {
50 field.type_.resolve(type_map)?;
51 }
52 Ok(())
53 }
54}
55
56impl Field {
57 pub fn from_idl(
58 ifield: &idl::Field,
59 ns: &Namespace,
60 builtin_types: &HashMap<String, String>,
61 ) -> Self {
62 let mut length: (Option<i64>, Option<i64>) = (None, None);
63 let mut format: Option<String> = None;
64 for option in &ifield.options {
65 match (option.name.as_str(), &option.value) {
66 ("length", idl::Value::Range(min, max)) => length = (*min, *max),
67 ("format", idl::Value::String(f)) => format = Some(f.clone()),
69 (name, _) => panic!("Unsupported option: {}", name),
70 }
71 }
72 Field {
73 name: ifield.name.clone(),
74 type_: Type::from_idl(&ifield.type_, ns, &builtin_types),
75 optional: ifield.optional,
76 length,
79 format,
80 position: ifield.position.clone(),
81 }
82 }
83}