1use std::fmt;
18
19use crate::{
20 Annotation,
21 ConstParameter,
22 Identifier,
23 Input,
24 Member,
25 Node,
26 NodeID,
27 Output,
28 TupleType,
29 Type,
30 indent_display::Indent,
31};
32use itertools::Itertools;
33use leo_span::Span;
34use serde::{Deserialize, Serialize};
35
36#[derive(Clone, Default, Debug, Serialize, Deserialize)]
38pub struct MappingPrototype {
39 pub identifier: Identifier,
41 pub key_type: Type,
43 pub value_type: Type,
45 pub span: Span,
47 pub id: NodeID,
49}
50
51impl PartialEq for MappingPrototype {
52 fn eq(&self, other: &Self) -> bool {
53 self.identifier == other.identifier
54 }
55}
56
57impl Eq for MappingPrototype {}
58
59impl fmt::Display for MappingPrototype {
60 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
61 write!(f, "mapping {}: {} => {};", self.identifier, self.key_type, self.value_type)
62 }
63}
64
65crate::simple_node_impl!(MappingPrototype);
66
67#[derive(Clone, Default, Debug, Serialize, Deserialize)]
69pub struct StorageVariablePrototype {
70 pub identifier: Identifier,
72 pub type_: Type,
74 pub span: Span,
76 pub id: NodeID,
78}
79
80impl PartialEq for StorageVariablePrototype {
81 fn eq(&self, other: &Self) -> bool {
82 self.identifier == other.identifier
83 }
84}
85
86impl Eq for StorageVariablePrototype {}
87
88impl fmt::Display for StorageVariablePrototype {
89 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
90 write!(f, "storage {}: {};", self.identifier, self.type_)
91 }
92}
93
94crate::simple_node_impl!(StorageVariablePrototype);
95
96#[derive(Clone, Default, Serialize, Deserialize)]
97pub struct FunctionPrototype {
98 pub annotations: Vec<Annotation>,
100 pub identifier: Identifier,
102 pub const_parameters: Vec<ConstParameter>,
104 pub input: Vec<Input>,
106 pub output: Vec<Output>,
108 pub output_type: Type,
110 pub span: Span,
112 pub id: NodeID,
114}
115
116impl FunctionPrototype {
117 #[allow(clippy::too_many_arguments)]
118 pub fn new(
119 annotations: Vec<Annotation>,
120 identifier: Identifier,
121 const_parameters: Vec<ConstParameter>,
122 input: Vec<Input>,
123 output: Vec<Output>,
124 span: Span,
125 id: NodeID,
126 ) -> Self {
127 let output_type = match output.len() {
128 0 => Type::Unit,
129 1 => output[0].type_.clone(),
130 _ => Type::Tuple(TupleType::new(output.iter().map(|o| o.type_.clone()).collect())),
131 };
132
133 Self { annotations, identifier, const_parameters, input, output, output_type, span, id }
134 }
135}
136
137impl PartialEq for FunctionPrototype {
138 fn eq(&self, other: &Self) -> bool {
139 self.identifier == other.identifier
140 }
141}
142
143impl Eq for FunctionPrototype {}
144
145impl fmt::Debug for FunctionPrototype {
146 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
147 write!(f, "{self}")
148 }
149}
150
151impl fmt::Display for FunctionPrototype {
152 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
153 for annotation in &self.annotations {
154 writeln!(f, "{annotation}")?;
155 }
156 write!(f, "fn {}", self.identifier)?;
157 if !self.const_parameters.is_empty() {
158 write!(f, "::[{}]", self.const_parameters.iter().format(", "))?;
159 }
160 write!(f, "({})", self.input.iter().format(", "))?;
161 match self.output.len() {
162 0 => {}
163 1 => {
164 if !matches!(self.output[0].type_, Type::Unit) {
165 write!(f, " -> {}", self.output[0])?;
166 }
167 }
168 _ => {
169 write!(f, " -> ({})", self.output.iter().format(", "))?;
170 }
171 }
172 write!(f, ";")
173 }
174}
175
176crate::simple_node_impl!(FunctionPrototype);
177
178#[derive(Clone, Default, Serialize, Deserialize)]
179pub struct RecordPrototype {
180 pub identifier: Identifier,
182 pub members: Vec<Member>,
184 pub span: Span,
186 pub id: NodeID,
188}
189
190impl PartialEq for RecordPrototype {
191 fn eq(&self, other: &Self) -> bool {
192 self.identifier == other.identifier
193 }
194}
195
196impl Eq for RecordPrototype {}
197
198impl fmt::Debug for RecordPrototype {
199 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
200 write!(f, "{self}")
201 }
202}
203
204impl fmt::Display for RecordPrototype {
205 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
206 writeln!(f, " record {} {{", self.identifier)?;
207
208 for field in self.members.iter() {
209 writeln!(f, "{},", Indent(field))?;
210 }
211 write!(f, "}}")
212 }
213}
214
215crate::simple_node_impl!(RecordPrototype);