bluejay_validator/executable/document/
path.rs1use bluejay_core::{
2 executable::{ExecutableDocument, FragmentDefinition, OperationDefinition},
3 Indexable,
4};
5use std::cmp::{Eq, Ord, Ordering, PartialEq, PartialOrd};
6use std::hash::{Hash, Hasher};
7
8pub struct Path<'a, E: ExecutableDocument> {
9 root: PathRoot<'a, E>,
10 members: Vec<&'a E::Selection>,
11}
12
13impl<E: ExecutableDocument> Clone for Path<'_, E> {
14 fn clone(&self) -> Self {
15 Self {
16 root: self.root,
17 members: self.members.clone(),
18 }
19 }
20}
21
22impl<'a, E: ExecutableDocument> Path<'a, E> {
23 pub fn new(root: PathRoot<'a, E>) -> Self {
24 Self {
25 root,
26 members: Vec::new(),
27 }
28 }
29
30 pub fn root(&self) -> &PathRoot<'a, E> {
31 &self.root
32 }
33
34 pub fn with_selection(&self, selection: &'a E::Selection) -> Self {
35 let mut clone = self.clone();
36 clone.members.push(selection);
37 clone
38 }
39
40 pub fn members(&self) -> &[&'a E::Selection] {
41 &self.members
42 }
43}
44
45pub enum PathRoot<'a, E: ExecutableDocument> {
46 Operation(&'a E::OperationDefinition),
47 Fragment(&'a E::FragmentDefinition),
48}
49
50impl<'a, E: ExecutableDocument + 'a> PathRoot<'a, E> {
51 pub fn name(&self) -> Option<&'a str> {
52 match self {
53 Self::Operation(o) => o.as_ref().name(),
54 Self::Fragment(f) => Some(f.name()),
55 }
56 }
57}
58
59impl<E: ExecutableDocument> Clone for PathRoot<'_, E> {
60 fn clone(&self) -> Self {
61 *self
62 }
63}
64
65impl<E: ExecutableDocument> Copy for PathRoot<'_, E> {}
66
67impl<E: ExecutableDocument> Hash for PathRoot<'_, E> {
68 fn hash<H: Hasher>(&self, state: &mut H) {
69 match self {
70 Self::Operation(o) => o.id().hash(state),
71 Self::Fragment(f) => f.id().hash(state),
72 }
73 }
74}
75
76impl<E: ExecutableDocument> PartialEq for PathRoot<'_, E> {
77 fn eq(&self, other: &Self) -> bool {
78 match (self, other) {
79 (Self::Operation(l), Self::Operation(r)) => l.id() == r.id(),
80 (Self::Fragment(l), Self::Fragment(r)) => l.id() == r.id(),
81 _ => false,
82 }
83 }
84}
85
86impl<E: ExecutableDocument> Eq for PathRoot<'_, E> {}
87
88impl<E: ExecutableDocument> Ord for PathRoot<'_, E> {
89 fn cmp(&self, other: &Self) -> Ordering {
90 match (self, other) {
91 (Self::Fragment(l), Self::Fragment(r)) => l.id().cmp(r.id()),
92 (Self::Fragment(_), Self::Operation(_)) => Ordering::Greater,
93 (Self::Operation(_), Self::Fragment(_)) => Ordering::Less,
94 (Self::Operation(l), Self::Operation(r)) => l.id().cmp(r.id()),
95 }
96 }
97}
98
99impl<E: ExecutableDocument> PartialOrd for PathRoot<'_, E> {
100 fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
101 Some(self.cmp(other))
102 }
103}