1mod grammar;
2
3use std::{cell::Cell, ops::Range};
4
5use crate::SyntaxKind;
6use grammar::{parse_QueryUnit, parse_UpdateUnit};
7use logos::Logos;
8use rowan::{GreenNode, GreenNodeBuilder, TextRange, TextSize};
9
10pub struct Parser {
11 tokens: Vec<Token>,
12 pos: usize,
13 fuel: Cell<u32>,
14 events: Vec<Event>,
15}
16
17#[derive(Debug, Clone)]
18pub(super) struct Token {
19 kind: SyntaxKind,
20 text: std::string::String,
21}
22
23impl Token {
24 fn is_trivia(&self) -> bool {
25 matches!(self.kind, SyntaxKind::WHITESPACE | SyntaxKind::Comment)
26 }
27
28 pub(super) fn kind(&self) -> SyntaxKind {
29 self.kind
30 }
31}
32
33#[derive(Debug)]
34pub struct ParseError {
35 pub span: TextRange,
36 pub message: String,
37}
38
39pub fn parse_text(input: &str, entry: TopEntryPoint) -> (GreenNode, Vec<ParseError>) {
40 let tokens = lex(input);
41 let parse_input = tokens
42 .iter()
43 .filter_map(|(token, _span)| (!token.is_trivia()).then_some(token))
44 .cloned()
45 .collect();
46 let output = entry.parse(parse_input);
47 build_tree(tokens, remove_empty_nodes(output))
48}
49
50fn remove_empty_nodes(events: Vec<Event>) -> Vec<Event> {
57 let mut remove = vec![false; events.len()];
58 let mut stack: Vec<(usize, bool)> = Vec::new();
60 for (index, event) in events.iter().enumerate() {
61 match event {
62 Event::Open { .. } => stack.push((index, false)),
63 Event::Advance => {
64 if let Some(top) = stack.last_mut() {
65 top.1 = true;
66 }
67 }
68 Event::Close => {
69 let (open_index, has_tokens) = stack
70 .pop()
71 .expect("Every \"Close\" event should occur after a open event");
72 if !has_tokens && !stack.is_empty() {
73 remove[open_index] = true;
74 remove[index] = true;
75 } else if has_tokens {
76 if let Some(parent) = stack.last_mut() {
77 parent.1 = true;
78 }
79 }
80 }
81 Event::Error { .. } => {}
82 }
83 }
84 events
85 .into_iter()
86 .zip(remove)
87 .filter_map(|(event, remove)| (!remove).then_some(event))
88 .collect()
89}
90
91fn build_tree(
92 tokens: Vec<(Token, Range<usize>)>,
93 events: Vec<Event>,
94) -> (GreenNode, Vec<ParseError>) {
95 let mut cursor = 0;
96 let mut builder = GreenNodeBuilder::new();
97 let mut erros: Vec<ParseError> = Vec::new();
98
99 for event in &events[..events.len() - 1] {
103 match event {
104 Event::Open { kind } => {
105 while !matches!(kind, SyntaxKind::QueryUnit | SyntaxKind::UpdateUnit)
106 && tokens
107 .get(cursor)
108 .map_or(false, |(next, _)| next.is_trivia())
109 {
110 let (token, _) = &tokens[cursor];
111 builder.token(token.kind.into(), &token.text);
112 cursor += 1;
113 }
114 builder.start_node((*kind).into());
115 }
116 Event::Error { expected } => {
117 let span = tokens[cursor..]
120 .iter()
121 .find(|(token, _)| !token.is_trivia())
122 .map(|(_, span)| {
123 TextRange::new(
124 TextSize::new(span.start as u32),
125 TextSize::new(span.end as u32),
126 )
127 })
128 .unwrap_or_else(|| {
129 let end = tokens[..cursor]
130 .iter()
131 .rev()
132 .find(|(token, _)| !token.is_trivia())
133 .map_or(0, |(_, span)| span.end as u32);
134 TextRange::new(TextSize::new(end), TextSize::new(end))
135 });
136 erros.push(ParseError {
137 span,
138 message: if expected.is_empty() {
139 "Syntax Error: unexpected token".to_string()
140 } else {
141 format!(
142 "Syntax Error: expected {}",
143 expected
144 .into_iter()
145 .map(|kind| format!("{kind:?}"))
146 .collect::<Vec<_>>()
147 .join(" or ")
148 )
149 },
150 });
151 }
152 Event::Close => {
153 builder.finish_node();
154 }
155
156 Event::Advance => {
157 while tokens
158 .get(cursor)
159 .map_or(false, |(next, _)| next.is_trivia())
160 {
161 let (token, _) = &tokens[cursor];
162 builder.token(token.kind.into(), &token.text);
163 cursor += 1;
164 }
165 let (token, _) = &tokens[cursor];
166 builder.token(token.kind.into(), &token.text);
167 cursor += 1;
168 }
169 }
170 }
171 assert!(matches!(events.last(), Some(Event::Close)));
173 while tokens
174 .get(cursor)
175 .map_or(false, |(next, _)| next.is_trivia())
176 {
177 let (token, _) = &tokens[cursor];
178 builder.token(token.kind.into(), &token.text);
179 cursor += 1;
180 }
181 builder.finish_node();
182 (builder.finish(), erros)
183}
184
185impl Parser {
186 fn new(input: Vec<Token>) -> Self {
187 Self {
188 tokens: input,
189 pos: 0,
190 fuel: 1024.into(),
191 events: Vec::new(),
192 }
193 }
194}
195
196#[derive(Debug)]
197enum Event {
198 Open { kind: SyntaxKind },
199 Error { expected: Vec<SyntaxKind> },
200 Close,
201 Advance,
202}
203
204const RECOVERY_TOKENS: &[SyntaxKind] = &[SyntaxKind::WHERE, SyntaxKind::LCurly, SyntaxKind::RCurly];
207
208struct MarkOpened {
209 index: usize,
210}
211
212impl Parser {
213 fn open(&mut self) -> MarkOpened {
214 let mark = MarkOpened {
215 index: self.events.len(),
216 };
217 self.events.push(Event::Open {
218 kind: SyntaxKind::Error,
219 });
220 mark
221 }
222
223 fn close(&mut self, m: MarkOpened, kind: SyntaxKind) {
224 self.events[m.index] = Event::Open { kind };
225 self.events.push(Event::Close);
226 }
227
228 fn advance(&mut self) {
229 assert!(!self.eof());
230 self.fuel.set(1024);
231 self.events.push(Event::Advance);
232 self.pos += 1;
233 }
234
235 fn eof(&self) -> bool {
236 self.pos == self.tokens.len()
237 }
238
239 fn nth(&self, lookahead: usize) -> SyntaxKind {
240 if self.fuel.get() == 0 {
241 panic!("parser is stuck")
242 }
243 self.fuel.set(self.fuel.get() - 1);
244 self.tokens
245 .get(self.pos + lookahead)
246 .map_or(SyntaxKind::Eof, |it| it.kind)
247 }
248
249 fn at(&self, kind: SyntaxKind) -> bool {
250 self.nth(0) == kind
251 }
252
253 fn at_any(&self, kinds: &[SyntaxKind]) -> bool {
254 let current = self.nth(0);
255 kinds.contains(¤t)
256 }
257
258 fn eat(&mut self, kind: SyntaxKind) -> bool {
259 if self.at(kind) {
260 self.advance();
261 true
262 } else {
263 false
264 }
265 }
266
267 fn expect(&mut self, kind: SyntaxKind) {
268 if self.eat(kind) {
269 return;
270 }
271 self.events.push(Event::Error {
272 expected: vec![kind],
273 });
274 }
275
276 fn advance_with_error(&mut self, expected: Vec<SyntaxKind>) {
277 self.events.push(Event::Error { expected });
278 if self.at_any(RECOVERY_TOKENS) {
282 return;
283 }
284 let m = self.open();
285 self.advance();
286 self.close(m, SyntaxKind::Error);
287 }
288
289 fn error_until(&mut self, expected: Vec<SyntaxKind>, recovery: &[SyntaxKind]) {
290 self.events.push(Event::Error { expected }); if self.at_any(recovery) || self.eof() {
292 return; }
294 let m = self.open();
295 while !self.at_any(recovery) && !self.eof() {
296 self.advance(); }
298 self.close(m, SyntaxKind::Error); }
300
301 pub(super) fn pos(&self) -> usize {
302 self.pos
303 }
304}
305
306#[derive(Debug)]
307pub enum TopEntryPoint {
308 QueryUnit,
309 UpdateUnit,
310}
311
312impl TopEntryPoint {
313 fn parse(&self, input: Vec<Token>) -> Vec<Event> {
314 let mut parser = Parser::new(input);
315 match self {
316 TopEntryPoint::QueryUnit => parse_QueryUnit(&mut parser),
317 TopEntryPoint::UpdateUnit => parse_UpdateUnit(&mut parser),
318 }
319 parser.events
320 }
321}
322
323pub(super) fn lex(text: &str) -> Vec<(Token, Range<usize>)> {
324 let mut lexer = SyntaxKind::lexer(text);
325 let mut tokens = Vec::new();
326
327 while let Some(result) = lexer.next() {
328 tokens.push((
329 Token {
330 kind: result.unwrap_or(SyntaxKind::Error),
331 text: lexer.slice().to_string(),
332 },
333 lexer.span(),
334 ));
335 }
336 tokens
337}
338
339pub fn guess_operation_type(input: &str) -> Option<TopEntryPoint> {
340 let tokens = lex(input);
341 tokens.iter().find_map(|(token, _)| match token.kind {
342 SyntaxKind::SELECT | SyntaxKind::CONSTRUCT | SyntaxKind::ASK | SyntaxKind::DESCRIBE => {
343 Some(TopEntryPoint::QueryUnit)
344 }
345 SyntaxKind::LOAD
346 | SyntaxKind::CLEAR
347 | SyntaxKind::DROP
348 | SyntaxKind::CREATE
349 | SyntaxKind::ADD
350 | SyntaxKind::MOVE
351 | SyntaxKind::COPY
352 | SyntaxKind::INSERT
353 | SyntaxKind::INSERT_DATA
354 | SyntaxKind::DELETE
355 | SyntaxKind::DELETE_DATA
356 | SyntaxKind::DELETE_WHERE => Some(TopEntryPoint::UpdateUnit),
357 _ => None,
358 })
359}
360
361#[cfg(test)]
362mod tests;