access_json/
query_executor.rs

1use crate::query::{JSONQuery, QueryElement};
2use crate::AnySerializable;
3use serde_json::Value as JSON;
4
5#[derive(Serialize, Deserialize, Debug, PartialEq)]
6enum State {
7    /// When we start serializing a Map element.
8    StartMap,
9    /// When we have encountered a Map key but still need to serialize it.
10    MapKey,
11    /// When we have encountered a Str in MapKey state.
12    MapKeyStr(String),
13    /// When we have the name of the field and begin serializing/visiting the MapValue.
14    MapValue,
15    /// Keep track of where we are, index of length:
16    Sequence(usize, usize),
17}
18
19#[derive(PartialEq, Eq, Debug, Serialize, Deserialize)]
20enum ElementKind {
21    Root,
22    List,
23    Map,
24}
25
26#[derive(Debug, Serialize, Deserialize)]
27pub struct OutputStackFrame {
28    kind: ElementKind,
29    list_items: Vec<JSON>,
30    map_keys: Vec<String>,
31    map_values: Vec<JSON>,
32}
33
34impl Default for OutputStackFrame {
35    fn default() -> Self {
36        Self {
37            kind: ElementKind::Root,
38            list_items: Vec::new(),
39            map_keys: Vec::new(),
40            map_values: Vec::new(),
41        }
42    }
43}
44impl OutputStackFrame {
45    fn list() -> OutputStackFrame {
46        Self {
47            kind: ElementKind::List,
48            ..Default::default()
49        }
50    }
51    fn map() -> OutputStackFrame {
52        Self {
53            kind: ElementKind::Map,
54            ..Default::default()
55        }
56    }
57    fn push_item(&mut self, item: JSON) {
58        debug_assert_ne!(self.kind, ElementKind::Map);
59        self.kind = ElementKind::List;
60        self.list_items.push(item);
61    }
62    fn push_key(&mut self, item: String) {
63        debug_assert_ne!(self.kind, ElementKind::List);
64        self.kind = ElementKind::Map;
65        self.map_keys.push(item);
66    }
67    fn push_value(&mut self, item: JSON) {
68        debug_assert_ne!(self.kind, ElementKind::List);
69        self.kind = ElementKind::Map;
70        self.map_values.push(item);
71    }
72    /// When we've wrapped the level above us, hope we know what type of thing we are!
73    fn push(&mut self, complex: OutputStackFrame) {
74        let value = complex.finish();
75        match self.kind {
76            ElementKind::Root => self.push_item(value),
77            ElementKind::List => self.push_item(value),
78            ElementKind::Map => self.push_value(value),
79        }
80    }
81    fn finish(self) -> JSON {
82        match self.kind {
83            ElementKind::Root => panic!("What's a ROOT? {:?}", self),
84            ElementKind::List => JSON::Array(self.list_items),
85            ElementKind::Map => {
86                debug_assert_eq!(self.map_values.len(), self.map_values.len());
87                let dict: serde_json::Map<String, JSON> = self
88                    .map_keys
89                    .into_iter()
90                    .zip(self.map_values.into_iter())
91                    .collect();
92                JSON::Object(dict)
93            }
94        }
95    }
96}
97
98enum NextStep<'a> {
99    NotMatching,
100    Found(&'a QueryElement),
101    IsMatch(&'a [QueryElement]),
102}
103
104#[derive(Serialize, Deserialize, Debug)]
105pub struct QueryExecutor {
106    query: Vec<QueryElement>,
107    current_path: Vec<QueryElement>,
108    state: Vec<State>,
109    output: Vec<OutputStackFrame>,
110}
111impl QueryExecutor {
112    pub fn new(query: &JSONQuery) -> Result<Self, QueryExecErr> {
113        Ok(Self {
114            query: query.elements.clone(),
115            current_path: Vec::new(),
116            state: Vec::new(),
117            // Keep a list on the bottom of the stack for single-value answers.
118            output: vec![Default::default()],
119        })
120    }
121    fn next_step(&self) -> NextStep<'_> {
122        let mut i = 0;
123        while i < self.query.len() && i < self.current_path.len() {
124            if self.query[i] != self.current_path[i] {
125                return NextStep::NotMatching;
126            }
127            i += 1;
128        }
129        // we have matched until one of us exhausted (query) or current_path.
130        if self.current_path.len() < self.query.len() {
131            NextStep::Found(&self.query[i])
132        } else {
133            NextStep::IsMatch(&self.current_path[i..])
134        }
135    }
136    /// Find the relative path to our current location, but only if we're matching the query.
137    fn relative_path(&self) -> Option<Vec<QueryElement>> {
138        match self.next_step() {
139            NextStep::IsMatch(relative) => Some(relative.to_vec()),
140            _ => None,
141        }
142    }
143    fn is_match(&self) -> bool {
144        self.relative_path().is_some()
145    }
146    fn possible_result(&mut self, found: &dyn AnySerializable) -> Result<(), QueryExecErr> {
147        if self.is_match() {
148            let output_frame = self.output.last_mut().unwrap();
149            match self.state.last().unwrap() {
150                State::MapKey | State::MapKeyStr(_) => panic!(
151                    "Shouldn't call possible_result here! {:?}, {:?}",
152                    self.state, self.current_path
153                ),
154                // StartMap is the state in which we visit struct fields.
155                State::StartMap | State::MapValue => {
156                    output_frame.push_value(serde_json::to_value(found)?)
157                }
158                State::Sequence(_, _) => output_frame.push_item(serde_json::to_value(found)?),
159            };
160        }
161        Ok(())
162    }
163    pub fn get_result(self) -> Option<JSON> {
164        debug_assert_eq!(self.output.len(), 1);
165        let output = &self.output[0];
166        match output.kind {
167            ElementKind::Root => output.list_items.get(0).cloned(),
168            ElementKind::List => output.list_items.get(0).cloned(),
169            ElementKind::Map => output.map_values.get(0).cloned(),
170        }
171    }
172
173    /// When we have recursive control over entering a scope or not, only enter if it advances our query match!
174    fn enter_name(&mut self, name: &str) -> bool {
175        let continues_match = match self.next_step() {
176            NextStep::IsMatch(_) => {
177                // write this name to output.
178                self.output.last_mut().unwrap().push_key(name.to_owned());
179                true
180            }
181            NextStep::Found(QueryElement::Field(field)) => name == field,
182            _ => false,
183        };
184        if continues_match {
185            self.current_path.push(QueryElement::field(name));
186        }
187        continues_match
188    }
189    /// Sometimes we do not have control over entering a scope; so we just push without checking whether it advances our match or not.
190    fn must_enter_name(&mut self, name: &str) {
191        self.current_path.push(QueryElement::field(name));
192        if self.is_match() {
193            // write this name to output.
194            self.output.last_mut().unwrap().push_key(name.to_owned());
195        }
196    }
197    fn exit_name(&mut self, name: Option<&str>) {
198        let top = self.current_path.pop();
199        if let Some(name) = name {
200            debug_assert_eq!(Some(QueryElement::field(name)), top);
201        }
202    }
203    fn enter_sequence(&mut self, length: Option<usize>) {
204        if self.is_match() {
205            self.output.push(OutputStackFrame::list());
206        }
207        self.state.push(State::Sequence(
208            0,
209            length.expect("All sequences have lengths?"),
210        ));
211    }
212    fn sequence_element<T: ?Sized>(&mut self, value: &T) -> Result<(), QueryExecErr>
213    where
214        T: serde::ser::Serialize,
215    {
216        let index = match self.state.pop() {
217            Some(State::Sequence(idx, len)) => {
218                assert!(idx < len);
219                self.state.push(State::Sequence(idx + 1, len));
220                idx
221            }
222            x => panic!(
223                "state should be sequence but was {:?}; path={:?}",
224                x, self.current_path
225            ),
226        };
227        if self.enter_index(index) {
228            value.serialize(&mut *self)?;
229            self.exit_index(index);
230        }
231        Ok(())
232    }
233    fn enter_index(&mut self, index: usize) -> bool {
234        let should_enter = match self.next_step() {
235            NextStep::NotMatching => false,
236            NextStep::Found(QueryElement::ArrayItem(x)) => (index == *x),
237            NextStep::Found(_) => false,
238            NextStep::IsMatch(_) => true,
239        };
240        if should_enter {
241            self.current_path.push(QueryElement::array_item(index));
242        }
243        should_enter
244    }
245    fn exit_index(&mut self, index: usize) {
246        let top = self.current_path.pop();
247        debug_assert_eq!(Some(QueryElement::array_item(index)), top);
248    }
249    fn exit_sequence(&mut self) -> Result<(), QueryExecErr> {
250        if self.is_match() {
251            // pop output stack and treat it as a value!
252            let top = self.output.pop().unwrap();
253            self.output.last_mut().unwrap().push(top);
254        }
255        let top = self.state.pop();
256        match top {
257            Some(State::Sequence(pos, len)) => {
258                debug_assert_eq!(pos, len);
259                Ok(())
260            }
261            found => Err(QueryExecErr::InternalError(format!(
262                "Bad exit_sequence state: {:?}",
263                found
264            ))),
265        }
266    }
267    fn enter_map(&mut self) {
268        if self.is_match() {
269            self.output.push(OutputStackFrame::map());
270        }
271        self.state.push(State::StartMap);
272    }
273    fn exit_map(&mut self) {
274        if self.is_match() && self.output.len() > 1 {
275            // pop output stack and treat it as a value!
276            let top = self.output.pop().unwrap();
277            self.output.last_mut().unwrap().push(top);
278        }
279        let top = self.state.pop();
280        debug_assert_eq!(top, Some(State::StartMap));
281    }
282    fn enter_map_key(&mut self) {
283        self.state.push(State::MapKey);
284    }
285    fn exit_map_key(&mut self) -> Result<(), QueryExecErr> {
286        // Leave MapKeyStr on state stack!
287        match self.state.last() {
288            Some(State::MapKeyStr(_)) => Ok(()),
289            _ => Err(QueryExecErr::InternalError(format!(
290                "Map key not a simple String! {:?}",
291                self.current_path
292            ))),
293        }
294    }
295    fn enter_map_value(&mut self) {
296        match self.state.last() {
297            Some(State::MapKeyStr(_)) => {}
298            _ => panic!(
299                "enter_map_value {:?} state={:?}",
300                self.current_path, self.state
301            ),
302        };
303        self.state.push(State::MapValue);
304    }
305    fn exit_map_value(&mut self) -> Result<(), QueryExecErr> {
306        match self.state.pop() {
307            Some(State::MapValue) => {}
308            actual => {
309                return Err(QueryExecErr::InternalError(format!(
310                    "Expected MapValue state, found: {:?}",
311                    actual
312                )))
313            }
314        }
315        match self.state.pop() {
316            Some(State::MapKeyStr(name)) => {
317                self.exit_name(Some(&name));
318            }
319            actual => {
320                return Err(QueryExecErr::InternalError(format!(
321                    "Expected MapKeyStr state, found: {:?}",
322                    actual
323                )))
324            }
325        }
326        match self.state.pop() {
327            Some(State::MapKey) => Ok(()),
328            actual => Err(QueryExecErr::InternalError(format!(
329                "Expected MapKey state, found: {:?}",
330                actual
331            ))),
332        }
333    }
334}
335
336/// An enum representing a runtime error given a correctly-parsed query.
337#[derive(Serialize, Deserialize, Debug, PartialEq, Eq)]
338pub enum QueryExecErr {
339    /// You gave us a query that has no fields or array accesses in it.
340    /// Just call serde_json::to_value instead of going through the query API!
341    EmptyQuery,
342    /// Basically a panic; please open a [github issue](https://github.com/jjfiv/access-json/issues), with data if possible!
343    InternalError(String),
344    /// Since we're currently implementing a serde Serializer to run the queries, we need a catch-all for custom errors, e.g., in user-specified serialization targets.
345    Serialization(String),
346}
347
348impl From<serde_json::Error> for QueryExecErr {
349    fn from(err: serde_json::Error) -> Self {
350        Self::InternalError(format!("{:?}", err))
351    }
352}
353
354impl std::fmt::Display for QueryExecErr {
355    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
356        write!(f, "{:?}", self)?;
357        Ok(())
358    }
359}
360impl std::error::Error for QueryExecErr {
361    fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
362        None
363    }
364    fn description(&self) -> &str {
365        "description() is deprecated; use Display"
366    }
367    fn cause(&self) -> Option<&dyn std::error::Error> {
368        self.source()
369    }
370}
371
372impl serde::ser::Error for QueryExecErr {
373    fn custom<T>(msg: T) -> Self
374    where
375        T: std::fmt::Display,
376    {
377        // Note: erased_serde brings us here on error.
378        QueryExecErr::Serialization(msg.to_string())
379    }
380}
381
382impl<'a> serde::Serializer for &'a mut QueryExecutor {
383    type Ok = ();
384    type Error = QueryExecErr;
385
386    type SerializeSeq = Self;
387    type SerializeTuple = Self;
388    type SerializeTupleStruct = Self;
389    type SerializeTupleVariant = Self;
390    type SerializeMap = Self;
391    type SerializeStruct = Self;
392    type SerializeStructVariant = Self;
393
394    fn serialize_bool(self, v: bool) -> Result<Self::Ok, Self::Error> {
395        self.possible_result(&v)
396    }
397    fn serialize_i8(self, v: i8) -> Result<Self::Ok, Self::Error> {
398        self.possible_result(&v)
399    }
400    fn serialize_i16(self, v: i16) -> Result<Self::Ok, Self::Error> {
401        self.possible_result(&v)
402    }
403    fn serialize_i32(self, v: i32) -> Result<Self::Ok, Self::Error> {
404        self.possible_result(&v)
405    }
406    fn serialize_i64(self, v: i64) -> Result<Self::Ok, Self::Error> {
407        self.possible_result(&v)
408    }
409    fn serialize_u8(self, v: u8) -> Result<Self::Ok, Self::Error> {
410        self.possible_result(&v)
411    }
412    fn serialize_u16(self, v: u16) -> Result<Self::Ok, Self::Error> {
413        self.possible_result(&v)
414    }
415    fn serialize_u32(self, v: u32) -> Result<Self::Ok, Self::Error> {
416        self.possible_result(&v)
417    }
418    fn serialize_u64(self, v: u64) -> Result<Self::Ok, Self::Error> {
419        self.possible_result(&v)
420    }
421    fn serialize_f32(self, v: f32) -> Result<Self::Ok, Self::Error> {
422        self.possible_result(&v)
423    }
424    fn serialize_f64(self, v: f64) -> Result<Self::Ok, Self::Error> {
425        self.possible_result(&v)
426    }
427    fn serialize_char(self, v: char) -> Result<Self::Ok, Self::Error> {
428        self.possible_result(&v)
429    }
430    fn serialize_str(self, v: &str) -> Result<Self::Ok, Self::Error> {
431        match self.state.last() {
432            Some(State::MapKey) => {
433                self.state.push(State::MapKeyStr(v.to_string()));
434                self.must_enter_name(v);
435                Ok(())
436            }
437            Some(State::MapKeyStr(_)) => Err(QueryExecErr::InternalError(
438                "Shouldn't see multiple str for the same key!".into(),
439            )),
440            Some(_) => self.possible_result(&v),
441            Option::None => Err(QueryExecErr::InternalError(
442                "&str value with no state!".into(),
443            )),
444        }
445    }
446    fn serialize_bytes(self, _v: &[u8]) -> Result<Self::Ok, Self::Error> {
447        unimplemented!()
448    }
449    fn serialize_none(self) -> Result<Self::Ok, Self::Error> {
450        self.serialize_unit()
451    }
452    fn serialize_some<T: ?Sized>(self, value: &T) -> Result<Self::Ok, Self::Error>
453    where
454        T: serde::Serialize,
455    {
456        value.serialize(self)
457    }
458    fn serialize_unit(self) -> Result<Self::Ok, Self::Error> {
459        self.possible_result(&serde_json::Value::Null)
460    }
461
462    fn serialize_unit_struct(self, _name: &'static str) -> Result<Self::Ok, Self::Error> {
463        // see test_unit_struct
464        self.serialize_unit()
465    }
466
467    fn serialize_unit_variant(
468        self,
469        _name: &'static str,
470        _variant_index: u32,
471        variant: &'static str,
472    ) -> Result<Self::Ok, Self::Error> {
473        // For unit variants of enums, we/serde serialize them as just a String.
474        // See test_enum_examples; Pet::Bird.
475        self.serialize_str(variant)?;
476        Ok(())
477    }
478    fn serialize_newtype_struct<T: ?Sized>(
479        self,
480        _name: &'static str,
481        value: &T,
482    ) -> Result<Self::Ok, Self::Error>
483    where
484        T: serde::Serialize,
485    {
486        // See test_newtype_struct:
487        // struct Meters(f64) is serialized as just a f64 and we don't care about the name of that type...?
488        value.serialize(&mut *self)
489    }
490    fn serialize_newtype_variant<T: ?Sized>(
491        self,
492        _name: &'static str,
493        _variant_index: u32,
494        variant: &'static str,
495        value: &T,
496    ) -> Result<Self::Ok, Self::Error>
497    where
498        T: serde::Serialize,
499    {
500        if self.enter_name(variant) {
501            value.serialize(&mut *self)?;
502            self.exit_name(Some(variant));
503        }
504        Ok(())
505    }
506    fn serialize_seq(self, len: Option<usize>) -> Result<Self::SerializeSeq, Self::Error> {
507        self.enter_sequence(len);
508        Ok(self)
509    }
510    fn serialize_tuple(self, len: usize) -> Result<Self::SerializeTuple, Self::Error> {
511        self.serialize_seq(Some(len))
512    }
513    fn serialize_tuple_struct(
514        self,
515        _name: &'static str,
516        len: usize,
517    ) -> Result<Self::SerializeTupleStruct, Self::Error> {
518        // TODO: what's a tuple-struct name in JSON output -- should be nothing?
519        self.serialize_seq(Some(len))
520    }
521    fn serialize_tuple_variant(
522        self,
523        _name: &'static str,
524        _variant_index: u32,
525        variant: &'static str,
526        len: usize,
527    ) -> Result<Self::SerializeTupleVariant, Self::Error> {
528        self.enter_map();
529        self.must_enter_name(variant);
530        self.enter_sequence(Some(len));
531        Ok(self)
532    }
533    fn serialize_map(self, _len: Option<usize>) -> Result<Self::SerializeMap, Self::Error> {
534        self.enter_map();
535        Ok(self)
536    }
537    fn serialize_struct(
538        self,
539        _name: &'static str,
540        len: usize,
541    ) -> Result<Self::SerializeStruct, Self::Error> {
542        self.serialize_map(Some(len))
543    }
544    fn serialize_struct_variant(
545        self,
546        _name: &'static str,
547        _variant_index: u32,
548        variant: &'static str,
549        _len: usize,
550    ) -> Result<Self::SerializeStructVariant, Self::Error> {
551        self.enter_map();
552        self.must_enter_name(variant);
553        Ok(self)
554    }
555}
556
557impl<'a> serde::ser::SerializeSeq for &'a mut QueryExecutor {
558    type Ok = ();
559    type Error = QueryExecErr;
560
561    fn serialize_element<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error>
562    where
563        T: serde::Serialize,
564    {
565        self.sequence_element(value)
566    }
567    fn end(self) -> Result<Self::Ok, Self::Error> {
568        self.exit_sequence()
569    }
570}
571
572impl<'a> serde::ser::SerializeMap for &'a mut QueryExecutor {
573    type Ok = ();
574    type Error = QueryExecErr;
575    fn serialize_key<T: ?Sized>(&mut self, key: &T) -> Result<(), Self::Error>
576    where
577        T: serde::Serialize,
578    {
579        // TODO not sure how to check this is a path we want.
580        // Serde does not enforce string-only keys, but JSON does.
581        // So we have a &T here and not a &str or &String like we'd want for checking.
582        self.enter_map_key();
583        key.serialize(&mut **self)?;
584        self.exit_map_key()
585    }
586    fn serialize_value<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error>
587    where
588        T: serde::Serialize,
589    {
590        self.enter_map_value();
591        value.serialize(&mut **self)?;
592        self.exit_map_value()
593    }
594    fn end(self) -> Result<Self::Ok, Self::Error> {
595        self.exit_map();
596        Ok(())
597    }
598}
599
600impl<'a> serde::ser::SerializeTuple for &'a mut QueryExecutor {
601    type Ok = ();
602    type Error = QueryExecErr;
603    fn serialize_element<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error>
604    where
605        T: serde::Serialize,
606    {
607        self.sequence_element(value)
608    }
609    fn end(self) -> Result<Self::Ok, Self::Error> {
610        self.exit_sequence()
611    }
612}
613impl<'a> serde::ser::SerializeTupleStruct for &'a mut QueryExecutor {
614    type Ok = ();
615    type Error = QueryExecErr;
616    fn serialize_field<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error>
617    where
618        T: serde::Serialize,
619    {
620        self.sequence_element(value)
621    }
622    fn end(self) -> Result<Self::Ok, Self::Error> {
623        self.exit_sequence()
624    }
625}
626impl<'a> serde::ser::SerializeTupleVariant for &'a mut QueryExecutor {
627    type Ok = ();
628    type Error = QueryExecErr;
629    fn serialize_field<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error>
630    where
631        T: serde::Serialize,
632    {
633        self.sequence_element(value)
634    }
635    fn end(self) -> Result<Self::Ok, Self::Error> {
636        self.exit_sequence()?;
637        self.exit_map();
638        self.exit_name(None);
639        Ok(())
640    }
641}
642impl<'a> serde::ser::SerializeStruct for &'a mut QueryExecutor {
643    type Ok = ();
644    type Error = QueryExecErr;
645    fn serialize_field<T: ?Sized>(
646        &mut self,
647        key: &'static str,
648        value: &T,
649    ) -> Result<(), Self::Error>
650    where
651        T: serde::Serialize,
652    {
653        if self.enter_name(key) {
654            value.serialize(&mut **self)?;
655            self.exit_name(Some(key));
656        }
657        Ok(())
658    }
659    fn end(self) -> Result<Self::Ok, Self::Error> {
660        self.exit_map();
661        Ok(())
662    }
663}
664
665impl<'a> serde::ser::SerializeStructVariant for &'a mut QueryExecutor {
666    type Ok = ();
667    type Error = QueryExecErr;
668    fn serialize_field<T: ?Sized>(
669        &mut self,
670        key: &'static str,
671        value: &T,
672    ) -> Result<(), Self::Error>
673    where
674        T: serde::Serialize,
675    {
676        if self.enter_name(key) {
677            value.serialize(&mut **self)?;
678            self.exit_name(Some(key));
679        }
680        Ok(())
681    }
682    fn end(self) -> Result<Self::Ok, Self::Error> {
683        self.exit_map();
684        self.exit_name(None);
685        Ok(())
686    }
687}