mirror of
https://github.com/aljazceru/turso.git
synced 2025-12-30 22:44:21 +01:00
Merge branch 'main' into perf-3
This commit is contained in:
@@ -982,6 +982,8 @@ pub enum AlterTableBody {
|
||||
RenameTo(Name),
|
||||
/// `ADD COLUMN`
|
||||
AddColumn(ColumnDefinition), // TODO distinction between ADD and ADD COLUMN
|
||||
/// `ALTER COLUMN`
|
||||
AlterColumn { old: Name, new: ColumnDefinition },
|
||||
/// `RENAME COLUMN`
|
||||
RenameColumn {
|
||||
/// old name
|
||||
|
||||
@@ -1409,6 +1409,13 @@ impl ToTokens for AlterTableBody {
|
||||
s.append(TK_COLUMNKW, None)?;
|
||||
def.to_tokens_with_context(s, context)
|
||||
}
|
||||
Self::AlterColumn { old, new } => {
|
||||
s.append(TK_ALTER, None)?;
|
||||
s.append(TK_COLUMNKW, None)?;
|
||||
old.to_tokens_with_context(s, context)?;
|
||||
s.append(TK_TO, None)?;
|
||||
new.to_tokens_with_context(s, context)
|
||||
}
|
||||
Self::RenameColumn { old, new } => {
|
||||
s.append(TK_RENAME, None)?;
|
||||
s.append(TK_COLUMNKW, None)?;
|
||||
|
||||
@@ -169,7 +169,7 @@ pub fn is_identifier_continue(b: u8) -> bool {
|
||||
|| b > b'\x7F'
|
||||
}
|
||||
|
||||
#[derive(Clone, PartialEq, Eq)] // do not derive Copy for Token, just use .clone() when needed
|
||||
#[derive(Clone, PartialEq, Eq, Debug)] // do not derive Copy for Token, just use .clone() when needed
|
||||
pub struct Token<'a> {
|
||||
pub value: &'a [u8],
|
||||
pub token_type: Option<TokenType>, // None means Token is whitespaces or comments
|
||||
|
||||
@@ -16,6 +16,9 @@ use crate::token::TokenType::{self, *};
|
||||
use crate::Result;
|
||||
use turso_macros::match_ignore_ascii_case;
|
||||
|
||||
const TRUE_LIT: &str = "TRUE";
|
||||
const FALSE_LIT: &str = "FALSE";
|
||||
|
||||
macro_rules! peek_expect {
|
||||
( $parser:expr, $( $x:ident ),* $(,)?) => {
|
||||
{
|
||||
@@ -419,7 +422,8 @@ impl<'a> Parser<'a> {
|
||||
}
|
||||
TK_COLUMNKW => {
|
||||
let prev_tt = self.current_token.token_type.unwrap_or(TK_EOF);
|
||||
let can_be_columnkw = matches!(prev_tt, TK_ADD | TK_RENAME | TK_DROP);
|
||||
let can_be_columnkw =
|
||||
matches!(prev_tt, TK_ADD | TK_RENAME | TK_DROP | TK_ALTER);
|
||||
|
||||
if !can_be_columnkw {
|
||||
tok.token_type = Some(TK_ID);
|
||||
@@ -1536,7 +1540,18 @@ impl<'a> Parser<'a> {
|
||||
Name::Ident(s) => Literal::String(s),
|
||||
})))
|
||||
} else {
|
||||
Ok(Box::new(Expr::Id(name)))
|
||||
match name {
|
||||
Name::Ident(s) => match s.as_str() {
|
||||
s if s.eq_ignore_ascii_case(TRUE_LIT) => {
|
||||
return Ok(Box::new(Expr::Literal(Literal::Numeric("1".into()))))
|
||||
}
|
||||
s if s.eq_ignore_ascii_case(FALSE_LIT) => {
|
||||
return Ok(Box::new(Expr::Literal(Literal::Numeric("0".into()))))
|
||||
}
|
||||
_ => return Ok(Box::new(Expr::Id(Name::Ident(s)))),
|
||||
},
|
||||
_ => Ok(Box::new(Expr::Id(name))),
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -3400,7 +3415,7 @@ impl<'a> Parser<'a> {
|
||||
Ok(result)
|
||||
}
|
||||
|
||||
fn parse_column_definition(&mut self, in_alter: bool) -> Result<ColumnDefinition> {
|
||||
pub fn parse_column_definition(&mut self, in_alter: bool) -> Result<ColumnDefinition> {
|
||||
let col_name = self.parse_nm()?;
|
||||
if !in_alter && col_name.as_str().eq_ignore_ascii_case("rowid") {
|
||||
return Err(Error::Custom("cannot use reserved word: ROWID".to_owned()));
|
||||
@@ -3419,7 +3434,7 @@ impl<'a> Parser<'a> {
|
||||
eat_assert!(self, TK_ALTER);
|
||||
eat_expect!(self, TK_TABLE);
|
||||
let tbl_name = self.parse_fullname(false)?;
|
||||
let tok = eat_expect!(self, TK_ADD, TK_DROP, TK_RENAME);
|
||||
let tok = eat_expect!(self, TK_ADD, TK_DROP, TK_RENAME, TK_ALTER);
|
||||
|
||||
match tok.token_type.unwrap() {
|
||||
TK_ADD => {
|
||||
@@ -3470,6 +3485,19 @@ impl<'a> Parser<'a> {
|
||||
}))
|
||||
}
|
||||
}
|
||||
TK_ALTER => {
|
||||
eat_expect!(self, TK_COLUMNKW);
|
||||
let col_name = self.parse_nm()?;
|
||||
|
||||
eat_expect!(self, TK_TO);
|
||||
|
||||
let new = self.parse_column_definition(true)?;
|
||||
|
||||
Ok(Stmt::AlterTable(AlterTable {
|
||||
name: tbl_name,
|
||||
body: AlterTableBody::AlterColumn { old: col_name, new },
|
||||
}))
|
||||
}
|
||||
_ => unreachable!(),
|
||||
}
|
||||
}
|
||||
@@ -9837,6 +9865,24 @@ mod tests {
|
||||
}),
|
||||
}))],
|
||||
),
|
||||
(
|
||||
b"ALTER TABLE foo ALTER COLUMN bar TO baz INTEGER".as_slice(),
|
||||
vec![Cmd::Stmt(Stmt::AlterTable (AlterTable {
|
||||
name: QualifiedName { db_name: None, name: Name::Ident("foo".to_owned()), alias: None },
|
||||
body: AlterTableBody::AlterColumn {
|
||||
old: Name::Ident("bar".to_owned()),
|
||||
new: ColumnDefinition {
|
||||
col_name: Name::Ident("baz".to_owned()),
|
||||
col_type: Some(Type {
|
||||
name: "INTEGER".to_owned(),
|
||||
size: None,
|
||||
}),
|
||||
constraints: vec![],
|
||||
},
|
||||
|
||||
},
|
||||
}))],
|
||||
),
|
||||
// parse create index
|
||||
(
|
||||
b"CREATE INDEX idx_foo ON foo (bar)".as_slice(),
|
||||
|
||||
Reference in New Issue
Block a user