diff --git a/lykiadb-lang/src/ast/visitor.rs b/lykiadb-lang/src/ast/visitor.rs index 81fbed4..d5c07bf 100644 --- a/lykiadb-lang/src/ast/visitor.rs +++ b/lykiadb-lang/src/ast/visitor.rs @@ -6,6 +6,10 @@ use super::{ stmt::Stmt, }; +pub trait ExprEvaluator { + fn eval(&mut self, e: &Expr) -> Result; +} + pub trait Visitor { fn visit_expr(&self, e: &Expr) -> Result; fn visit_stmt(&self, s: &Stmt) -> Result; diff --git a/lykiadb-server/src/engine/interpreter.rs b/lykiadb-server/src/engine/interpreter.rs index 4a8db26..fbc64c5 100644 --- a/lykiadb-server/src/engine/interpreter.rs +++ b/lykiadb-server/src/engine/interpreter.rs @@ -1,6 +1,6 @@ use lykiadb_lang::ast::expr::{Expr, Operation}; use lykiadb_lang::ast::stmt::Stmt; -use lykiadb_lang::ast::visitor::VisitorMut; +use lykiadb_lang::ast::visitor::{ExprEvaluator, VisitorMut}; use lykiadb_lang::parser::program::Program; use lykiadb_lang::parser::resolver::Resolver; use lykiadb_lang::parser::Parser; @@ -71,12 +71,6 @@ pub enum InterpretError { span: Span, property: String, }, - /*AssignmentToUndefined { - token: Token, - }, - VariableNotFound { - token: Token, - },*/ Other { message: String, }, // TODO(vck): Refactor this @@ -180,7 +174,12 @@ pub struct Interpreter { env_man: Shared, source_processor: SourceProcessor, current_program: Option>, - planner: Planner +} + +impl ExprEvaluator for Interpreter { + fn eval(&mut self, e: &Expr) -> Result { + self.visit_expr(e) + } } impl Interpreter { @@ -193,7 +192,6 @@ impl Interpreter { loop_stack: LoopStack::new(), source_processor: SourceProcessor::new(), current_program: None, - planner: Planner::new() } } @@ -328,7 +326,11 @@ impl VisitorMut for Interpreter { Expr::Select { .. } | Expr::Insert { .. } | Expr::Update { .. } | - Expr::Delete { .. } => /*self.planner.build(&e)*/ Ok(RV::NaN), + Expr::Delete { .. } => { + let mut planner = Planner::new(); + let plan = planner.build(e)?; + Ok(RV::Undefined) + }, Expr::Literal { value, raw: _, diff --git a/lykiadb-server/src/net/tcp.rs b/lykiadb-server/src/net/tcp.rs index 4f5dca5..72f9720 100644 --- a/lykiadb-server/src/net/tcp.rs +++ b/lykiadb-server/src/net/tcp.rs @@ -18,7 +18,6 @@ impl TcpConnection { pub async fn read(&mut self) -> Result, CommunicationError> { loop { - // TODO(vck): Replace .to_vec call with something cheaper if let Ok(parsed) = bson::from_slice::(&self.read_buffer) { self.read_buffer.clear(); return Ok(Some(parsed)); diff --git a/lykiadb-server/src/plan/mod.rs b/lykiadb-server/src/plan/mod.rs index e69de29..446a2ab 100644 --- a/lykiadb-server/src/plan/mod.rs +++ b/lykiadb-server/src/plan/mod.rs @@ -0,0 +1,42 @@ +use lykiadb_lang::ast::sql::SqlExpr; +use serde::{Deserialize, Serialize}; +pub mod planner; + +#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)] +pub enum Aggregate { + Average(SqlExpr), + Count(SqlExpr), + Max(SqlExpr), + Min(SqlExpr), + Sum(SqlExpr), +} + +#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)] +pub enum Direction { + Ascending, + Descending, +} + +#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)] +pub enum Plan { + Select(Node) +} + +#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)] +pub enum Node { + Aggregate { source: Box, group_by: Vec, aggregates: Vec }, + + Filter { source: Box, predicate: SqlExpr }, + + Projection { source: Box, expressions: Vec, aliases: Vec }, + + Scan { collection: String, filter: Option, alias: Option }, + + Limit { source: Box, limit: usize }, + + Offset { source: Box, offset: usize }, + + Order { source: Box, key: Vec<(SqlExpr, Direction)> }, + + Values { rows: Vec> }, +} \ No newline at end of file diff --git a/lykiadb-server/src/plan/planner.rs b/lykiadb-server/src/plan/planner.rs new file mode 100644 index 0000000..bdbca03 --- /dev/null +++ b/lykiadb-server/src/plan/planner.rs @@ -0,0 +1,28 @@ +use lykiadb_lang::ast::{expr::Expr, sql::SqlSelect, visitor::ExprEvaluator}; + +use crate::{engine::interpreter::HaltReason, value::types::RV}; + +use super::{Node, Plan}; +pub struct Planner; + +impl Planner { + pub fn new() -> Planner { + Planner {} + } + + pub fn build(&mut self, expr: &Expr) -> Result { + match expr { + Expr::Select { + query, + span: _, + id: _ } => { + self.build_select(query) + }, + _ => panic!("Not implemented yet.") + } + } + + fn build_select(&mut self, query: &SqlSelect) -> Result { + Ok(Plan::Select(Node::Values { rows: vec![vec![]] })) + } +} \ No newline at end of file diff --git a/lykiadb-server/src/plan/tree.rs b/lykiadb-server/src/plan/tree.rs deleted file mode 100644 index e69de29..0000000 diff --git a/lykiadb-server/src/value/environment.rs b/lykiadb-server/src/value/environment.rs index 8e749a4..64dc580 100644 --- a/lykiadb-server/src/value/environment.rs +++ b/lykiadb-server/src/value/environment.rs @@ -30,6 +30,12 @@ impl Default for Environment { #[derive(Debug, Clone, Serialize, Deserialize)] pub enum EnvironmentError { + /*AssignmentToUndefined { + token: Token, + }, + VariableNotFound { + token: Token, + },*/ Other { message: String, }