Refine CREATE TABLE and CREATE INDEX
This commit is contained in:
parent
d555e8565f
commit
0aa3b28e74
1 changed files with 49 additions and 29 deletions
78
src/main.rs
78
src/main.rs
|
|
@ -90,7 +90,7 @@ impl DbValue {
|
|||
// table-metadata and data
|
||||
|
||||
type TableName = String;
|
||||
type TablePosition = u32;
|
||||
type TablePosition = usize;
|
||||
|
||||
struct Table {
|
||||
schema: TableSchema,
|
||||
|
|
@ -117,10 +117,6 @@ struct TableSchema {
|
|||
types: Vec<DbType>,
|
||||
}
|
||||
|
||||
// TODO
|
||||
fn column_position(table_meta: TableSchema, column_name: ColumnName) -> Option<ColumnPosition> {
|
||||
todo!()
|
||||
}
|
||||
// Use `TablePosition` as index
|
||||
type Tables = Vec<Table>;
|
||||
|
||||
|
|
@ -146,17 +142,35 @@ fn select_columns(row: &Row, columns: &Vec<ColumnPosition>) -> Row {
|
|||
|
||||
// ==============Interpreter================
|
||||
struct State {
|
||||
table_positions: HashMap<TableName, TablePosition>,
|
||||
table_name_position_mapping: BiMap<TableName, TablePosition>,
|
||||
tables: Vec<Table>,
|
||||
}
|
||||
|
||||
impl State {
|
||||
fn table_from_name<'b: 'a, 'a>(&'b self, table_name: TableName) -> Option<&'a Table> {
|
||||
todo!()
|
||||
fn table_from_name<'b: 'a, 'a>(&'b self, table_name: &TableName) -> DbResult<&'a Table> {
|
||||
match self.table_name_position_mapping.get_by_left(table_name) {
|
||||
Some(table_position) => {
|
||||
let table = &self.tables[*table_position];
|
||||
Ok(table)
|
||||
},
|
||||
None => Err(Error::TableDoesNotExist(table_name.clone()))
|
||||
}
|
||||
}
|
||||
|
||||
fn table_from_name_mut<'b: 'a, 'a>(&'b mut self, table_name: &TableName) -> DbResult<&'a mut Table> {
|
||||
match self.table_name_position_mapping.get_by_left(table_name) {
|
||||
Some(table_position) => {
|
||||
let table = &mut self.tables[*table_position];
|
||||
Ok(table)
|
||||
},
|
||||
None => Err(Error::TableDoesNotExist(table_name.clone()))
|
||||
}
|
||||
}
|
||||
|
||||
fn attach_table(&mut self, table_name: TableName, table: Table) {
|
||||
todo!()
|
||||
let new_table_position: TablePosition = self.tables.len();
|
||||
self.table_name_position_mapping.insert(table_name, new_table_position);
|
||||
self.tables.push(table);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -165,13 +179,6 @@ trait SqlConsumer {
|
|||
// TODO:
|
||||
}
|
||||
|
||||
// TODO: This should return a reference to the table
|
||||
// 'tables_life contains 'table_life
|
||||
fn get_table<'tables_life: 'table_life, 'table_life>(tables: &'tables_life Tables, table_name: &TableName) -> &'table_life Table {
|
||||
// let table_position:
|
||||
todo!()
|
||||
}
|
||||
|
||||
// TODO: Decide if we want for this to return a response (but then you have to deal with lifetimes,
|
||||
// because you'll be forced to put an iterator/slice into the Response data-structure.
|
||||
// Alternative is to pass a row-consumer to the functionas that knows how to communicate with
|
||||
|
|
@ -182,17 +189,17 @@ fn interpret(table_name: TableName, operation: Operation, state: &mut State, con
|
|||
|
||||
match operation {
|
||||
Select(table_name, column_selection, maybe_condition) => {
|
||||
let table: &Table = todo!();
|
||||
let table: &Table = state.table_from_name(&table_name)?;
|
||||
Ok(Response::Selected(table.select_where(column_selection, maybe_condition)?))
|
||||
},
|
||||
Insert(table_name, values) => {
|
||||
let table: &mut Table = todo!();
|
||||
let table: &mut Table = state.table_from_name_mut(&table_name)?;
|
||||
|
||||
let _ = table.insert(values)?;
|
||||
Ok(Response::Inserted())
|
||||
Ok(Response::Inserted)
|
||||
},
|
||||
Delete(table_name, maybe_condition) => {
|
||||
let table: &mut Table = todo!();
|
||||
let table: &mut Table = state.table_from_name_mut(&table_name)?;
|
||||
|
||||
let rows_affected = table.delete_where(maybe_condition)?;
|
||||
Ok(Response::Deleted(rows_affected))
|
||||
|
|
@ -200,22 +207,28 @@ fn interpret(table_name: TableName, operation: Operation, state: &mut State, con
|
|||
CreateTable(table_name, table_schema) => {
|
||||
let table = Table::new(table_schema);
|
||||
state.attach_table(table_name, table);
|
||||
todo!()
|
||||
Ok(Response::TableCreated)
|
||||
},
|
||||
CreateIndex(table_name, column_name) => {
|
||||
let table: &mut Table = todo!();
|
||||
let column_position: ColumnPosition = todo!();
|
||||
// TODO: This is incomplete. It can happen that an index is created
|
||||
// after the table has some rows for a while.
|
||||
// In such a case the index needs to be built over all those existing rows.
|
||||
let table: &mut Table = state.table_from_name_mut(&table_name)?;
|
||||
let column_position: ColumnPosition = table.schema.column_position_from_column_name(&column_name)?;
|
||||
|
||||
let index: ColumnIndex = ColumnIndex::new();
|
||||
let index: ColumnIndex = ColumnIndex::new(&table.rows);
|
||||
table.attach_index(column_position, index);
|
||||
todo!()
|
||||
Ok(Response::IndexCreated)
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
impl ColumnIndex {
|
||||
fn new() -> Self {
|
||||
Self { index: BTreeMap::new() }
|
||||
fn new(rows: &Rows) -> Self {
|
||||
let index = BTreeMap::new();
|
||||
// TODO: Take into account already existing rows
|
||||
todo!();
|
||||
Self { index }
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -236,6 +249,10 @@ impl TableSchema {
|
|||
}
|
||||
}
|
||||
|
||||
fn column_position_from_column_name(&self, column_name: &ColumnName) -> DbResult<ColumnPosition> {
|
||||
self.get_column(column_name).map(|(_, column_position)| column_position)
|
||||
}
|
||||
|
||||
fn is_primary(&self, column_position: ColumnPosition) -> bool {
|
||||
self.primary_key == column_position
|
||||
}
|
||||
|
|
@ -243,7 +260,7 @@ impl TableSchema {
|
|||
fn column_positions_from_column_names(&self, column_names: &[ColumnName]) -> DbResult<Vec<ColumnPosition>> {
|
||||
let mut positions: Vec<ColumnPosition> = Vec::with_capacity(column_names.len());
|
||||
for column_name in column_names {
|
||||
let (_, column_position) = self.get_column(column_name)?;
|
||||
let column_position = self.column_position_from_column_name(column_name)?;
|
||||
positions.push(column_position)
|
||||
}
|
||||
Ok(positions)
|
||||
|
|
@ -512,14 +529,17 @@ impl ColumnIndex {
|
|||
|
||||
enum Response {
|
||||
Selected(Vec<Row>),
|
||||
Inserted(),
|
||||
Inserted,
|
||||
Deleted(usize), // how many were deleted
|
||||
TableCreated,
|
||||
IndexCreated,
|
||||
}
|
||||
|
||||
type DbResult<A> = Result<A, Error>;
|
||||
|
||||
// #[derive(Debug)]
|
||||
enum Error {
|
||||
TableDoesNotExist(TableName),
|
||||
ColumnDoesNotExist(TableName, ColumnName),
|
||||
ColumnPositionDoesNotExist(TableName, ColumnPosition),
|
||||
ValueDoesNotMatchExpectedType(TableName, ColumnName, DbType, DbValue),
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue