From 8794ea9898d1edfb991246287f7d00ca2f3d8767 Mon Sep 17 00:00:00 2001 From: Piotr Sarna Date: Wed, 26 Apr 2023 19:29:26 +0200 Subject: [PATCH] query_analysis: allow CREATE FUNCTION statement --- sqld/src/query_analysis.rs | 45 +++++++++++++++++++++++++++----------- 1 file changed, 32 insertions(+), 13 deletions(-) diff --git a/sqld/src/query_analysis.rs b/sqld/src/query_analysis.rs index 0217d29d..1d3160c3 100644 --- a/sqld/src/query_analysis.rs +++ b/sqld/src/query_analysis.rs @@ -200,25 +200,44 @@ impl Statement { is_insert, }) } + + // Workaround for CREATE FUNCTION. + // FIXME: this should be handled by the parser (or *at least* trimmed + case insensitive) + let is_create_function = s.starts_with("CREATE FUNCTION"); + let mut maybe_create_function_stmt = is_create_function.then(|| { + Ok(Statement { + stmt: s.to_string(), + kind: StmtKind::Other, + is_iud: false, + is_insert: false, + }) + }); + // The parser needs to be boxed because it's large, and you don't want it on the stack. // There's upstream work to make it smaller, but in the meantime the parser should remain // on the heap: // - https://github.com/gwenn/lemon-rs/issues/8 // - https://github.com/gwenn/lemon-rs/pull/19 let mut parser = Box::new(Parser::new(s.as_bytes())); - std::iter::from_fn(move || match parser.next() { - Ok(Some(cmd)) => Some(parse_inner(s, cmd)), - Ok(None) => None, - Err(sqlite3_parser::lexer::sql::Error::ParserError( - ParserError::SyntaxError { - token_type: _, - found: Some(found), - }, - Some((line, col)), - )) => Some(Err(anyhow::anyhow!( - "syntax error around L{line}:{col}: `{found}`" - ))), - Err(e) => Some(Err(e.into())), + std::iter::from_fn(move || { + if is_create_function { + return maybe_create_function_stmt.take(); + } + + match parser.next() { + Ok(Some(cmd)) => Some(parse_inner(s, cmd)), + Ok(None) => None, + Err(sqlite3_parser::lexer::sql::Error::ParserError( + ParserError::SyntaxError { + token_type: _, + found: Some(found), + }, + Some((line, col)), + )) => Some(Err(anyhow::anyhow!( + "syntax error around L{line}:{col}: `{found}`" + ))), + Err(e) => Some(Err(e.into())), + } }) }