simple_triplestore/mem/
query.rs

1use crate::{
2    prelude::*,
3    traits::{IdType, Property},
4    Query, QueryError, Triple,
5};
6
7use super::MemTripleStore;
8
9impl<Id: IdType, NodeProps: Property, EdgeProps: Property>
10    TripleStoreQuery<Id, NodeProps, EdgeProps> for MemTripleStore<Id, NodeProps, EdgeProps>
11{
12    type QueryResult = MemTripleStore<Id, NodeProps, EdgeProps>;
13    type QueryResultError = ();
14
15    fn run(
16        &self,
17        query: Query<Id>,
18    ) -> Result<
19        MemTripleStore<Id, NodeProps, EdgeProps>,
20        QueryError<Self::Error, Self::QueryResultError>,
21    > {
22        Ok(match query {
23            Query::NodeProps(nodes) => {
24                let mut result =
25                    MemTripleStore::new_from_boxed_id_generator(self.id_generator.clone());
26                for node in nodes {
27                    if let Some(data) = self.node_props.get(&node) {
28                        result.node_props.insert(node, data.clone());
29                    }
30                }
31                result
32            }
33
34            Query::SPO(triples) => {
35                let mut result =
36                    MemTripleStore::new_from_boxed_id_generator(self.id_generator.clone());
37                for (sub, pred, obj) in triples.into_iter() {
38                    let triple = Triple { sub, pred, obj };
39                    if let Some(data_id) = self.spo_data.get(&Id::encode_spo_triple(&triple)) {
40                        if let Some(data) = self.edge_props.get(&data_id) {
41                            result
42                                .insert_edge(triple, data.clone())
43                                .map_err(|e| QueryError::Right(e))?;
44                        }
45                    }
46                }
47                result
48            }
49
50            Query::S(items) => {
51                let mut result =
52                    MemTripleStore::new_from_boxed_id_generator(self.id_generator.clone());
53                for sub in items {
54                    for (key, data_id) in self.spo_data.range(Id::key_bounds_1(sub)) {
55                        if let Some(data) = self.edge_props.get(&data_id) {
56                            result
57                                .insert_edge(Id::decode_spo_triple(&key), data.clone())
58                                .map_err(|e| QueryError::Right(e))?;
59                        }
60                    }
61                }
62                result
63            }
64
65            Query::SP(items) => {
66                let mut result =
67                    MemTripleStore::new_from_boxed_id_generator(self.id_generator.clone());
68                for (sub, pred) in items {
69                    for (key, data_id) in self.spo_data.range(Id::key_bounds_2(sub, pred)) {
70                        if let Some(data) = self.edge_props.get(&data_id) {
71                            result
72                                .insert_edge(Id::decode_spo_triple(&key), data.clone())
73                                .map_err(|e| QueryError::Right(e))?;
74                        }
75                    }
76                }
77                result
78            }
79
80            Query::SO(items) => {
81                let mut result =
82                    MemTripleStore::new_from_boxed_id_generator(self.id_generator.clone());
83                for (sub, obj) in items {
84                    for (key, data_id) in self.osp_data.range(Id::key_bounds_2(obj, sub)) {
85                        if let Some(data) = self.edge_props.get(&data_id) {
86                            result
87                                .insert_edge(Id::decode_osp_triple(key), data.clone())
88                                .map_err(|e| QueryError::Right(e))?;
89                        }
90                    }
91                }
92                result
93            }
94
95            Query::P(items) => {
96                let mut result =
97                    MemTripleStore::new_from_boxed_id_generator(self.id_generator.clone());
98                for pred in items {
99                    for (key, data_id) in self.pos_data.range(Id::key_bounds_1(pred)) {
100                        if let Some(data) = self.edge_props.get(&data_id) {
101                            result
102                                .insert_edge(Id::decode_pos_triple(key), data.clone())
103                                .map_err(|e| QueryError::Right(e))?;
104                        }
105                    }
106                }
107                result
108            }
109
110            Query::PO(items) => {
111                let mut result =
112                    MemTripleStore::new_from_boxed_id_generator(self.id_generator.clone());
113                for (pred, obj) in items {
114                    for (key, data_id) in self.pos_data.range(Id::key_bounds_2(pred, obj)) {
115                        if let Some(data) = self.edge_props.get(&data_id) {
116                            result
117                                .insert_edge(Id::decode_pos_triple(key), data.clone())
118                                .map_err(|e| QueryError::Right(e))?;
119                        }
120                    }
121                }
122                result
123            }
124
125            Query::O(items) => {
126                let mut result =
127                    MemTripleStore::new_from_boxed_id_generator(self.id_generator.clone());
128                for obj in items {
129                    for (key, data_id) in self.osp_data.range(Id::key_bounds_1(obj)) {
130                        if let Some(data) = self.edge_props.get(&data_id) {
131                            result
132                                .insert_edge(Id::decode_osp_triple(key), data.clone())
133                                .map_err(|e| QueryError::Right(e))?;
134                        }
135                    }
136                }
137                result
138            }
139        })
140    }
141}
142
143#[cfg(test)]
144mod test {
145    use crate::{MemTripleStore, UlidIdGenerator};
146
147    #[test]
148    fn test_query_node_props() {
149        crate::conformance::query::test_query_node_props(MemTripleStore::new(
150            UlidIdGenerator::new(),
151        ));
152    }
153
154    #[test]
155    fn test_query_edge_props() {
156        crate::conformance::query::test_query_edge_props(MemTripleStore::new(
157            UlidIdGenerator::new(),
158        ));
159    }
160
161    #[test]
162    fn test_query_s() {
163        crate::conformance::query::test_query_s(MemTripleStore::new(UlidIdGenerator::new()));
164    }
165
166    #[test]
167    fn test_query_sp() {
168        crate::conformance::query::test_query_sp(MemTripleStore::new(UlidIdGenerator::new()));
169    }
170
171    #[test]
172    fn test_query_p() {
173        crate::conformance::query::test_query_p(MemTripleStore::new(UlidIdGenerator::new()));
174    }
175
176    #[test]
177    fn test_query_po() {
178        crate::conformance::query::test_query_po(MemTripleStore::new(UlidIdGenerator::new()));
179    }
180
181    #[test]
182    fn test_query_o() {
183        crate::conformance::query::test_query_o(MemTripleStore::new(UlidIdGenerator::new()));
184    }
185
186    #[test]
187    fn test_query_os() {
188        crate::conformance::query::test_query_os(MemTripleStore::new(UlidIdGenerator::new()));
189    }
190}