uqa_storage/catalog/
graph_access.rs1use crate::{StorageBackendError, StorageBackendResult};
11
12#[derive(Debug, Clone, Copy, PartialEq, Eq)]
13pub enum GraphEntityKind {
14 Vertex,
15 Edge,
16}
17
18impl GraphEntityKind {
19 pub fn as_str(self) -> &'static str {
20 match self {
21 Self::Vertex => "vertex",
22 Self::Edge => "edge",
23 }
24 }
25}
26
27#[derive(Debug, Clone, Copy)]
30pub struct GraphEntityFilter<'a> {
31 pub kind: GraphEntityKind,
32 pub graph: Option<&'a str>,
33 pub label: Option<&'a str>,
34 pub source: Option<u64>,
35 pub target: Option<u64>,
36}
37
38#[derive(Debug, Clone, Copy, PartialEq, Eq)]
40pub enum GraphEntitySelector<'a> {
41 All,
42 Graph(&'a str),
43 Label(&'a str),
44 Source(u64),
45 Target(u64),
46}
47
48impl<'a> GraphEntityFilter<'a> {
49 pub fn new(kind: GraphEntityKind, graph: Option<&'a str>) -> Self {
50 Self {
51 kind,
52 graph,
53 label: None,
54 source: None,
55 target: None,
56 }
57 }
58
59 pub fn validate(self) -> StorageBackendResult<()> {
60 if self.kind == GraphEntityKind::Vertex && (self.source.is_some() || self.target.is_some())
61 {
62 return Err(StorageBackendError::Other(
63 "vertex scans cannot have edge endpoint filters".into(),
64 ));
65 }
66 Ok(())
67 }
68
69 pub fn selector(self) -> StorageBackendResult<GraphEntitySelector<'a>> {
70 self.validate()?;
71 Ok(if let Some(source) = self.source {
72 GraphEntitySelector::Source(source)
73 } else if let Some(target) = self.target {
74 GraphEntitySelector::Target(target)
75 } else if let Some(label) = self.label {
76 GraphEntitySelector::Label(label)
77 } else if let Some(graph) = self.graph {
78 GraphEntitySelector::Graph(graph)
79 } else {
80 GraphEntitySelector::All
81 })
82 }
83}
84
85pub const MAX_GRAPH_ID_PAGE: usize = 4096;
87
88pub fn validate_graph_page(limit: usize) -> StorageBackendResult<()> {
89 if !(1..=MAX_GRAPH_ID_PAGE).contains(&limit) {
90 return Err(StorageBackendError::Other(format!(
91 "graph identity page size must be in 1..={MAX_GRAPH_ID_PAGE}"
92 )));
93 }
94 Ok(())
95}