async_graphql_parser/types/
executable.rs1use serde::{Deserialize, Serialize};
4
5use super::*;
6
7#[derive(Debug, Clone, Serialize, Deserialize)]
11pub struct ExecutableDocument {
12 pub operations: DocumentOperations,
14 pub fragments: HashMap<Name, Positioned<FragmentDefinition>>,
16}
17
18#[derive(Debug, Clone, Serialize, Deserialize)]
22pub enum DocumentOperations {
23 Single(Positioned<OperationDefinition>),
25 Multiple(HashMap<Name, Positioned<OperationDefinition>>),
27}
28
29impl DocumentOperations {
30 #[must_use]
32 pub fn iter(&self) -> OperationsIter<'_> {
33 OperationsIter(match self {
34 Self::Single(op) => OperationsIterInner::Single(Some(op)),
35 Self::Multiple(ops) => OperationsIterInner::Multiple(ops.iter()),
36 })
37 }
38}
39
40#[derive(Debug, Clone)]
54pub struct OperationsIter<'a>(OperationsIterInner<'a>);
55
56impl<'a> Iterator for OperationsIter<'a> {
57 type Item = (Option<&'a Name>, &'a Positioned<OperationDefinition>);
58
59 fn next(&mut self) -> Option<Self::Item> {
60 match &mut self.0 {
61 OperationsIterInner::Single(op) => op.take().map(|op| (None, op)),
62 OperationsIterInner::Multiple(iter) => iter.next().map(|(name, op)| (Some(name), op)),
63 }
64 }
65
66 fn size_hint(&self) -> (usize, Option<usize>) {
67 let size = self.len();
68 (size, Some(size))
69 }
70}
71
72impl std::iter::FusedIterator for OperationsIter<'_> {}
73
74impl ExactSizeIterator for OperationsIter<'_> {
75 fn len(&self) -> usize {
76 match &self.0 {
77 OperationsIterInner::Single(opt) => usize::from(opt.is_some()),
78 OperationsIterInner::Multiple(iter) => iter.len(),
79 }
80 }
81}
82
83#[derive(Debug, Clone)]
84enum OperationsIterInner<'a> {
85 Single(Option<&'a Positioned<OperationDefinition>>),
86 Multiple(hash_map::Iter<'a, Name, Positioned<OperationDefinition>>),
87}
88
89#[derive(Debug, Clone, Serialize, Deserialize)]
94pub struct OperationDefinition {
95 pub ty: OperationType,
97 pub variable_definitions: Vec<Positioned<VariableDefinition>>,
99 pub directives: Vec<Positioned<Directive>>,
101 pub selection_set: Positioned<SelectionSet>,
103}
104
105#[derive(Debug, Clone, Serialize, Deserialize)]
110pub struct VariableDefinition {
111 pub name: Positioned<Name>,
113 pub var_type: Positioned<Type>,
115 pub directives: Vec<Positioned<Directive>>,
117 pub default_value: Option<Positioned<ConstValue>>,
119}
120
121impl VariableDefinition {
122 #[must_use]
125 pub fn default_value(&self) -> Option<&ConstValue> {
126 self.default_value.as_ref().map(|value| &value.node).or({
127 if self.var_type.node.nullable {
128 Some(&ConstValue::Null)
129 } else {
130 None
131 }
132 })
133 }
134}
135
136#[derive(Debug, Default, Clone, Serialize, Deserialize)]
140pub struct SelectionSet {
141 pub items: Vec<Positioned<Selection>>,
143}
144
145#[derive(Debug, Clone, Serialize, Deserialize)]
150pub enum Selection {
151 Field(Positioned<Field>),
154 FragmentSpread(Positioned<FragmentSpread>),
156 InlineFragment(Positioned<InlineFragment>),
158}
159
160impl Selection {
161 #[must_use]
163 pub fn directives(&self) -> &Vec<Positioned<Directive>> {
164 match self {
165 Self::Field(field) => &field.node.directives,
166 Self::FragmentSpread(spread) => &spread.node.directives,
167 Self::InlineFragment(fragment) => &fragment.node.directives,
168 }
169 }
170 #[must_use]
172 pub fn directives_mut(&mut self) -> &mut Vec<Positioned<Directive>> {
173 match self {
174 Self::Field(field) => &mut field.node.directives,
175 Self::FragmentSpread(spread) => &mut spread.node.directives,
176 Self::InlineFragment(fragment) => &mut fragment.node.directives,
177 }
178 }
179}
180
181#[derive(Debug, Clone, Serialize, Deserialize)]
186pub struct Field {
187 pub alias: Option<Positioned<Name>>,
189 pub name: Positioned<Name>,
191 pub arguments: Vec<(Positioned<Name>, Positioned<Value>)>,
193 pub directives: Vec<Positioned<Directive>>,
195 pub selection_set: Positioned<SelectionSet>,
198}
199
200impl Field {
201 #[must_use]
204 pub fn response_key(&self) -> &Positioned<Name> {
205 self.alias.as_ref().unwrap_or(&self.name)
206 }
207
208 #[must_use]
210 pub fn get_argument(&self, name: &str) -> Option<&Positioned<Value>> {
211 self.arguments
212 .iter()
213 .find(|item| item.0.node == name)
214 .map(|item| &item.1)
215 }
216}
217
218#[derive(Debug, Clone, Serialize, Deserialize)]
222pub struct FragmentSpread {
223 pub fragment_name: Positioned<Name>,
225 pub directives: Vec<Positioned<Directive>>,
227}
228
229#[derive(Debug, Clone, Serialize, Deserialize)]
233pub struct InlineFragment {
234 pub type_condition: Option<Positioned<TypeCondition>>,
236 pub directives: Vec<Positioned<Directive>>,
238 pub selection_set: Positioned<SelectionSet>,
240}
241
242#[derive(Debug, Clone, Serialize, Deserialize)]
247pub struct FragmentDefinition {
248 pub type_condition: Positioned<TypeCondition>,
250 pub directives: Vec<Positioned<Directive>>,
252 pub selection_set: Positioned<SelectionSet>,
254}
255
256#[derive(Debug, Clone, Serialize, Deserialize)]
260pub struct TypeCondition {
261 pub on: Positioned<Name>,
263}