1use lora_analyzer::symbols::VarId;
2use lora_analyzer::{
3 ResolvedClause, ResolvedExpr, ResolvedMergeAction, ResolvedPattern, ResolvedPatternPart,
4 ResolvedProjection, ResolvedRemoveItem, ResolvedSetItem, ResolvedSortItem,
5};
6use lora_ast::{Direction, RangeLiteral};
7
8pub type PhysicalNodeId = usize;
9
10#[derive(Debug, Clone)]
11pub struct PhysicalPlan {
12 pub root: PhysicalNodeId,
13 pub nodes: Vec<PhysicalOp>,
14}
15
16#[derive(Debug, Clone)]
17pub enum PhysicalOp {
18 Argument(ArgumentExec),
19 NodeScan(NodeScanExec),
20 NodeByLabelScan(NodeByLabelScanExec),
21 NodeByIdSeek(NodeByIdSeekExec),
22 NodeByPropertyScan(NodeByPropertyScanExec),
23 NodeByPropertyRangeScan(NodeByPropertyRangeScanExec),
24 NodeByTextScan(NodeByTextScanExec),
25 NodeByPointScan(NodeByPointScanExec),
26 RelByPropertyRangeScan(RelByPropertyRangeScanExec),
27 RelByTextScan(RelByTextScanExec),
28 RelByPointScan(RelByPointScanExec),
29 RelByIdSeek(RelByIdSeekExec),
30 Expand(ExpandExec),
31 Filter(FilterExec),
32 Projection(ProjectionExec),
33 Unwind(UnwindExec),
34 HashAggregation(HashAggregationExec),
35 Sort(SortExec),
36 Limit(LimitExec),
37 Create(CreateExec),
38 Merge(MergeExec),
39 Delete(DeleteExec),
40 Set(SetExec),
41 Remove(RemoveExec),
42 Foreach(ForeachExec),
43 OptionalMatch(OptionalMatchExec),
44 PathBuild(PathBuildExec),
45 CallSubquery(CallSubqueryExec),
46}
47
48#[derive(Debug, Clone)]
50pub struct ForeachExec {
51 pub input: PhysicalNodeId,
52 pub variable: VarId,
53 pub list: ResolvedExpr,
54 pub body: Vec<ResolvedClause>,
55}
56
57#[derive(Debug, Clone)]
59pub struct CallSubqueryExec {
60 pub input: PhysicalNodeId,
61 pub inner: PhysicalNodeId,
62 pub new_vars: Vec<VarId>,
63}
64
65#[derive(Debug, Clone)]
66pub struct PathBuildExec {
67 pub input: PhysicalNodeId,
68 pub output: VarId,
69 pub node_vars: Vec<VarId>,
70 pub rel_vars: Vec<VarId>,
71 pub shortest_path_all: Option<bool>,
72}
73
74#[derive(Debug, Clone)]
77pub struct OptionalMatchExec {
78 pub input: PhysicalNodeId,
79 pub inner: PhysicalNodeId,
80 pub new_vars: Vec<VarId>,
81}
82
83#[derive(Debug, Clone)]
84pub struct ArgumentExec;
85
86#[derive(Debug, Clone)]
87pub struct NodeScanExec {
88 pub input: Option<PhysicalNodeId>,
89 pub var: VarId,
90}
91
92#[derive(Debug, Clone)]
93pub struct NodeByLabelScanExec {
94 pub input: Option<PhysicalNodeId>,
95 pub var: VarId,
96 pub labels: Vec<Vec<String>>,
98}
99
100#[derive(Debug, Clone)]
102pub struct NodeByIdSeekExec {
103 pub input: Option<PhysicalNodeId>,
104 pub var: VarId,
105 pub labels: Vec<Vec<String>>,
106 pub ids: ResolvedExpr,
107 pub in_list: bool,
108}
109
110#[derive(Debug, Clone)]
111pub struct NodeByPropertyScanExec {
112 pub input: Option<PhysicalNodeId>,
113 pub var: VarId,
114 pub labels: Vec<Vec<String>>,
116 pub key: String,
117 pub value: ResolvedExpr,
118 pub in_list: bool,
121}
122
123#[derive(Debug, Clone)]
124pub struct NodeByPropertyRangeScanExec {
125 pub input: Option<PhysicalNodeId>,
126 pub var: VarId,
127 pub labels: Vec<Vec<String>>,
128 pub key: String,
129 pub lo: Option<ResolvedExpr>,
130 pub lo_inclusive: bool,
131 pub hi: Option<ResolvedExpr>,
132 pub hi_inclusive: bool,
133 pub order: Option<lora_ast::SortDirection>,
137}
138
139#[derive(Debug, Clone)]
140pub struct NodeByTextScanExec {
141 pub input: Option<PhysicalNodeId>,
142 pub var: VarId,
143 pub labels: Vec<Vec<String>>,
144 pub key: String,
145 pub predicate: crate::logical::TextPredicate,
146 pub query: ResolvedExpr,
147}
148
149#[derive(Debug, Clone)]
150pub struct NodeByPointScanExec {
151 pub input: Option<PhysicalNodeId>,
152 pub var: VarId,
153 pub labels: Vec<Vec<String>>,
154 pub key: String,
155 pub predicate: crate::logical::PointPredicate,
156}
157
158#[derive(Debug, Clone)]
159pub struct RelByPropertyRangeScanExec {
160 pub input: Option<PhysicalNodeId>,
161 pub src: VarId,
162 pub rel: VarId,
163 pub dst: VarId,
164 pub types: Vec<String>,
165 pub direction: Direction,
166 pub key: String,
167 pub lo: Option<ResolvedExpr>,
168 pub lo_inclusive: bool,
169 pub hi: Option<ResolvedExpr>,
170 pub hi_inclusive: bool,
171}
172
173#[derive(Debug, Clone)]
174pub struct RelByTextScanExec {
175 pub input: Option<PhysicalNodeId>,
176 pub src: VarId,
177 pub rel: VarId,
178 pub dst: VarId,
179 pub types: Vec<String>,
180 pub direction: Direction,
181 pub key: String,
182 pub predicate: crate::logical::TextPredicate,
183 pub query: ResolvedExpr,
184}
185
186#[derive(Debug, Clone)]
187pub struct RelByPointScanExec {
188 pub input: Option<PhysicalNodeId>,
189 pub src: VarId,
190 pub rel: VarId,
191 pub dst: VarId,
192 pub types: Vec<String>,
193 pub direction: Direction,
194 pub key: String,
195 pub predicate: crate::logical::PointPredicate,
196}
197
198#[derive(Debug, Clone)]
200pub struct RelByIdSeekExec {
201 pub input: Option<PhysicalNodeId>,
202 pub src: VarId,
203 pub src_labels: Vec<Vec<String>>,
204 pub rel: VarId,
205 pub dst: VarId,
206 pub types: Vec<String>,
207 pub direction: Direction,
208 pub ids: ResolvedExpr,
209 pub in_list: bool,
210}
211
212#[derive(Debug, Clone)]
213pub struct ExpandExec {
214 pub input: PhysicalNodeId,
215 pub src: VarId,
216 pub rel: Option<VarId>,
217 pub dst: VarId,
218 pub types: Vec<String>,
219 pub direction: Direction,
220 pub rel_properties: Option<ResolvedExpr>,
221 pub range: Option<RangeLiteral>,
222}
223
224#[derive(Debug, Clone)]
225pub struct FilterExec {
226 pub input: PhysicalNodeId,
227 pub predicate: ResolvedExpr,
228}
229
230#[derive(Debug, Clone)]
231pub struct ProjectionExec {
232 pub input: PhysicalNodeId,
233 pub distinct: bool,
234 pub items: Vec<ResolvedProjection>,
235 pub include_existing: bool,
236}
237
238#[derive(Debug, Clone)]
239pub struct UnwindExec {
240 pub input: PhysicalNodeId,
241 pub expr: ResolvedExpr,
242 pub alias: VarId,
243}
244
245#[derive(Debug, Clone)]
246pub struct HashAggregationExec {
247 pub input: PhysicalNodeId,
248 pub group_by: Vec<ResolvedProjection>,
249 pub aggregates: Vec<ResolvedProjection>,
250}
251
252#[derive(Debug, Clone)]
253pub struct SortExec {
254 pub input: PhysicalNodeId,
255 pub items: Vec<ResolvedSortItem>,
256 pub top_k: Option<usize>,
258 pub limit: Option<crate::logical::SortLimit>,
261}
262
263#[derive(Debug, Clone)]
264pub struct LimitExec {
265 pub input: PhysicalNodeId,
266 pub skip: Option<ResolvedExpr>,
267 pub limit: Option<ResolvedExpr>,
268}
269
270#[derive(Debug, Clone)]
271pub struct CreateExec {
272 pub input: PhysicalNodeId,
273 pub pattern: ResolvedPattern,
274}
275
276#[derive(Debug, Clone)]
277pub struct MergeExec {
278 pub input: PhysicalNodeId,
279 pub pattern_part: ResolvedPatternPart,
280 pub actions: Vec<ResolvedMergeAction>,
281}
282
283#[derive(Debug, Clone)]
284pub struct DeleteExec {
285 pub input: PhysicalNodeId,
286 pub detach: bool,
287 pub expressions: Vec<ResolvedExpr>,
288}
289
290#[derive(Debug, Clone)]
291pub struct SetExec {
292 pub input: PhysicalNodeId,
293 pub items: Vec<ResolvedSetItem>,
294}
295
296#[derive(Debug, Clone)]
297pub struct RemoveExec {
298 pub input: PhysicalNodeId,
299 pub items: Vec<ResolvedRemoveItem>,
300}