Introduce new simplified Operation type for Interpreter
This commit is contained in:
parent
cf76cc4d10
commit
935d9814ae
4 changed files with 110 additions and 3 deletions
|
|
@ -1,4 +1,5 @@
|
||||||
use crate::type_system::Value;
|
use crate::type_system::Value;
|
||||||
|
use crate::operation::InsertionValuesForInterpreter;
|
||||||
use std::ops::{Index, IndexMut};
|
use std::ops::{Index, IndexMut};
|
||||||
use std::slice::SliceIndex;
|
use std::slice::SliceIndex;
|
||||||
|
|
||||||
|
|
@ -42,6 +43,10 @@ impl Row {
|
||||||
Row(vec![])
|
Row(vec![])
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn new_from_insertion_values(insertion_values: InsertionValuesForInterpreter) -> Self {
|
||||||
|
Row(insertion_values)
|
||||||
|
}
|
||||||
|
|
||||||
pub fn with_number_of_columns(number_of_columns: usize) -> Self {
|
pub fn with_number_of_columns(number_of_columns: usize) -> Self {
|
||||||
Row(Vec::with_capacity(number_of_columns))
|
Row(Vec::with_capacity(number_of_columns))
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -2,7 +2,7 @@ use crate::error::Error;
|
||||||
use crate::internals::row::{ColumnPosition, Row};
|
use crate::internals::row::{ColumnPosition, Row};
|
||||||
use crate::schema::{TableName, TableSchema};
|
use crate::schema::{TableName, TableSchema};
|
||||||
use crate::internals::table::Table;
|
use crate::internals::table::Table;
|
||||||
use crate::operation::{ColumnSelection, Condition, Operation};
|
use crate::operation::{ColumnSelection, Condition, Operation, OperationForInterpreter, ConditionForInterpreter, ColumnSelectionForInterpreter};
|
||||||
use crate::result::DbResult;
|
use crate::result::DbResult;
|
||||||
use crate::type_system::{DbType, IndexableValue, Value};
|
use crate::type_system::{DbType, IndexableValue, Value};
|
||||||
use bimap::BiMap;
|
use bimap::BiMap;
|
||||||
|
|
@ -65,6 +65,7 @@ impl State {
|
||||||
m
|
m
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: Get rid of this
|
||||||
fn table_from_name<'a>(&'a self, table_name: &TableName) -> DbResult<&'a Table> {
|
fn table_from_name<'a>(&'a self, table_name: &TableName) -> DbResult<&'a Table> {
|
||||||
match self.table_name_position_mapping.get_by_left(table_name) {
|
match self.table_name_position_mapping.get_by_left(table_name) {
|
||||||
Some(table_position) => {
|
Some(table_position) => {
|
||||||
|
|
@ -75,6 +76,10 @@ impl State {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn table_at<'a>(&'a self, table_position: TablePosition) -> &'a Table {
|
||||||
|
&self.tables[table_position]
|
||||||
|
}
|
||||||
|
|
||||||
fn table_from_name_mut<'b: 'a, 'a>(
|
fn table_from_name_mut<'b: 'a, 'a>(
|
||||||
&'b mut self,
|
&'b mut self,
|
||||||
table_name: &TableName,
|
table_name: &TableName,
|
||||||
|
|
@ -88,6 +93,10 @@ impl State {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn table_at_mut<'a>(&'a mut self, table_position: TablePosition) -> &'a mut Table {
|
||||||
|
&mut self.tables[table_position]
|
||||||
|
}
|
||||||
|
|
||||||
fn attach_table(&mut self, table_name: TableName, table: Table) {
|
fn attach_table(&mut self, table_name: TableName, table: Table) {
|
||||||
let new_table_position: TablePosition = self.tables.len();
|
let new_table_position: TablePosition = self.tables.len();
|
||||||
self.table_name_position_mapping
|
self.table_name_position_mapping
|
||||||
|
|
@ -95,7 +104,67 @@ impl State {
|
||||||
self.tables.push(table);
|
self.tables.push(table);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn interpret<'a>(&'a mut self, operation: Operation) -> DbResult<Response<'a>> {
|
pub fn interpret_for_interpreter<'a>(&'a mut self, operation: OperationForInterpreter) -> DbResult<Response<'a>> {
|
||||||
|
// TODO: lock stuff
|
||||||
|
use OperationForInterpreter::*;
|
||||||
|
|
||||||
|
match operation {
|
||||||
|
Select(table_position, column_selection, maybe_condition) => {
|
||||||
|
let table: &Table = self.table_at(table_position);
|
||||||
|
|
||||||
|
let selected_rows = match maybe_condition {
|
||||||
|
None => {
|
||||||
|
let x = table.select_all_rows(column_selection);
|
||||||
|
Box::new(x) as Box<dyn Iterator<Item=Row> + 'a + Send>
|
||||||
|
},
|
||||||
|
|
||||||
|
Some(ConditionForInterpreter::Eq(eq_column, value)) => {
|
||||||
|
let x =
|
||||||
|
table.select_rows_where_eq(
|
||||||
|
column_selection,
|
||||||
|
eq_column,
|
||||||
|
value,
|
||||||
|
)?;
|
||||||
|
Box::new(x) as Box<dyn Iterator<Item=Row> + 'a + Send>
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
Ok(Response::Selected(selected_rows))
|
||||||
|
},
|
||||||
|
Insert(table_position, values) => {
|
||||||
|
let table: &mut Table = self.table_at_mut(table_position);
|
||||||
|
|
||||||
|
let (id, row) = table.schema().row_from_insertion_values_for_interpreter(values)?;
|
||||||
|
table.insert_row_at(id, row)?;
|
||||||
|
Ok(Response::Inserted)
|
||||||
|
}
|
||||||
|
Delete(table_position, maybe_condition) => {
|
||||||
|
let table: &mut Table = self.table_at_mut(table_position);
|
||||||
|
|
||||||
|
let rows_affected = match maybe_condition {
|
||||||
|
None => table.delete_all_rows(),
|
||||||
|
Some(ConditionForInterpreter::Eq(eq_column, value)) => {
|
||||||
|
table.delete_rows_where_eq(eq_column, value)?
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
Ok(Response::Deleted(rows_affected))
|
||||||
|
}
|
||||||
|
CreateTable(table_name, table_schema) => {
|
||||||
|
let table = Table::new(table_schema);
|
||||||
|
self.attach_table(table_name, table);
|
||||||
|
|
||||||
|
Ok(Response::TableCreated)
|
||||||
|
}
|
||||||
|
CreateIndex(table_position, column) => {
|
||||||
|
let table: &mut Table = self.table_at_mut(table_position);
|
||||||
|
table.attach_index(column)?;
|
||||||
|
Ok(Response::IndexCreated)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn interpret<'a>(&'a mut self, operation: Operation) -> DbResult<Response<'a>> {
|
||||||
// TODO: lock stuff
|
// TODO: lock stuff
|
||||||
use Operation::*;
|
use Operation::*;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,7 @@
|
||||||
use crate::schema::{ColumnName, TableName, TableSchema};
|
use crate::schema::{ColumnName, TableName, TableSchema};
|
||||||
use crate::type_system::Value;
|
use crate::type_system::Value;
|
||||||
|
use crate::internals::row::ColumnPosition;
|
||||||
|
use crate::interpreter::TablePosition;
|
||||||
|
|
||||||
// ==============SQL operations================
|
// ==============SQL operations================
|
||||||
// TODO: Note that every operation has a table name.
|
// TODO: Note that every operation has a table name.
|
||||||
|
|
@ -16,13 +18,25 @@ pub enum Operation {
|
||||||
// DropTable(TableName),
|
// DropTable(TableName),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub enum OperationForInterpreter {
|
||||||
|
Select(TablePosition, ColumnSelectionForInterpreter, Option<ConditionForInterpreter>),
|
||||||
|
Insert(TablePosition, InsertionValuesForInterpreter),
|
||||||
|
Delete(TablePosition, Option<ConditionForInterpreter>),
|
||||||
|
CreateTable(TableName, TableSchema),
|
||||||
|
CreateIndex(TablePosition, ColumnPosition),
|
||||||
|
}
|
||||||
|
|
||||||
pub type InsertionValues = Vec<(ColumnName, Value)>;
|
pub type InsertionValues = Vec<(ColumnName, Value)>;
|
||||||
|
|
||||||
|
pub type InsertionValuesForInterpreter = Vec<Value>;
|
||||||
|
|
||||||
pub enum ColumnSelection {
|
pub enum ColumnSelection {
|
||||||
All,
|
All,
|
||||||
Columns(Vec<ColumnName>),
|
Columns(Vec<ColumnName>),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub type ColumnSelectionForInterpreter = Vec<ColumnPosition>;
|
||||||
|
|
||||||
pub enum Condition {
|
pub enum Condition {
|
||||||
// And(Box<Condition>, Box<Condition>),
|
// And(Box<Condition>, Box<Condition>),
|
||||||
// Or(Box<Condition>, Box<Condition>),
|
// Or(Box<Condition>, Box<Condition>),
|
||||||
|
|
@ -34,6 +48,10 @@ pub enum Condition {
|
||||||
// StringCondition(StringCondition),
|
// StringCondition(StringCondition),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub enum ConditionForInterpreter {
|
||||||
|
Eq(ColumnPosition, Value),
|
||||||
|
}
|
||||||
|
|
||||||
// enum StringCondition {
|
// enum StringCondition {
|
||||||
// Prefix(ColumnName, String),
|
// Prefix(ColumnName, String),
|
||||||
// Substring(ColumnName, String),
|
// Substring(ColumnName, String),
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
use crate::error::Error;
|
use crate::error::Error;
|
||||||
use crate::internals::row::{ColumnPosition, Row};
|
use crate::internals::row::{ColumnPosition, Row};
|
||||||
use crate::operation::{ColumnSelection, InsertionValues};
|
use crate::operation::{ColumnSelection, InsertionValues, InsertionValuesForInterpreter, ColumnSelectionForInterpreter};
|
||||||
use crate::result::DbResult;
|
use crate::result::DbResult;
|
||||||
use crate::type_system::{DbType, IndexableValue, Uuid, Value};
|
use crate::type_system::{DbType, IndexableValue, Uuid, Value};
|
||||||
use bimap::BiMap;
|
use bimap::BiMap;
|
||||||
|
|
@ -136,6 +136,21 @@ impl TableSchema {
|
||||||
self.column_name_position_mapping.len()
|
self.column_name_position_mapping.len()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn row_from_insertion_values_for_interpreter(
|
||||||
|
&self,
|
||||||
|
insertion_values: InsertionValuesForInterpreter,
|
||||||
|
) -> DbResult<(Uuid, Row)> {
|
||||||
|
let row: Row = Row::new_from_insertion_values(insertion_values);
|
||||||
|
|
||||||
|
let id: Uuid = match row.get(self.primary_key) {
|
||||||
|
Some(Value::Indexable(IndexableValue::Uuid(id))) => *id,
|
||||||
|
Some(_) => unreachable!(), // SAFETY: Should be guaranteed by validation
|
||||||
|
None => unreachable!(), // SAFETY: Should be guaranteed by validation
|
||||||
|
};
|
||||||
|
|
||||||
|
Ok((id, row))
|
||||||
|
}
|
||||||
|
|
||||||
pub fn row_from_insertion_values(
|
pub fn row_from_insertion_values(
|
||||||
&self,
|
&self,
|
||||||
insertion_values: InsertionValues,
|
insertion_values: InsertionValues,
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue