diff --git a/src/lib/CreateStatement.h b/src/lib/CreateStatement.h index bd3394d..d7059a5 100644 --- a/src/lib/CreateStatement.h +++ b/src/lib/CreateStatement.h @@ -18,12 +18,14 @@ typedef enum { struct CreateStatement : Statement { CreateStatement() : Statement(kStmtCreate), + if_not_exists(false), file_path(NULL), table_name(NULL) {}; virtual ~CreateStatement(); // defined in destructors.cpp CreateType create_type; + bool if_not_exists; const char* file_path; const char* table_name; }; diff --git a/src/parser/bison_parser.y b/src/parser/bison_parser.y index 807751d..c84c48b 100644 --- a/src/parser/bison_parser.y +++ b/src/parser/bison_parser.y @@ -76,6 +76,7 @@ typedef void* yyscan_t; int64_t ival; char* sval; uint uval; + bool bval; hsql::Statement* statement; hsql::SelectStatement* select_stmt; @@ -106,11 +107,11 @@ typedef void* yyscan_t; /* SQL Keywords */ %token DATABASE DISTINCT BETWEEN CONTROL NATURAL COLUMN -%token CREATE DELETE HAVING IMPORT INSERT ISNULL OFFSET -%token RENAME SELECT UNLOAD UPDATE ALTER CROSS GROUP INDEX -%token INNER LIMIT ORDER OUTER RIGHT TABLE UNION USING WHERE -%token DESC DROP FILE FROM INTO JOIN LEFT LIKE LOAD NULL ALL -%token AND ASC CSV NOT TBL TOP AS BY IN IS ON OR +%token CREATE DELETE EXISTS HAVING IMPORT INSERT ISNULL +%token OFFSET RENAME SELECT UNLOAD UPDATE ALTER CROSS GROUP +%token INDEX INNER LIMIT ORDER OUTER RIGHT TABLE UNION USING +%token WHERE DESC DROP FILE FROM INTO JOIN LEFT LIKE LOAD +%token NULL ALL AND ASC CSV NOT TBL TOP AS BY IF IN IS ON OR /********************************* @@ -122,6 +123,7 @@ typedef void* yyscan_t; %type import_statement %type create_statement %type table_name opt_alias alias file_path +%type opt_not_exists %type from_clause table_ref table_ref_atomic table_ref_name %type
join_clause join_table %type expr scalar_expr unary_expr binary_expr function_expr star_expr expr_alias @@ -212,14 +214,19 @@ file_path: ** Create Statement ******************************/ create_statement: - CREATE TABLE table_name FROM TBL FILE file_path { + CREATE TABLE opt_not_exists table_name FROM TBL FILE file_path { $$ = new CreateStatement(); $$->create_type = kTableFromTbl; - $$->file_path = $7; - $$->table_name = $3; + $$->if_not_exists = $3; + $$->table_name = $4; + $$->file_path = $8; } ; +opt_not_exists: + IF NOT EXISTS { $$ = true; } + | /* empty */ { $$ = false; } + ; /****************************** ** Select Statement diff --git a/src/parser/flex_lexer.l b/src/parser/flex_lexer.l index ae7e529..6b1a518 100644 --- a/src/parser/flex_lexer.l +++ b/src/parser/flex_lexer.l @@ -65,6 +65,7 @@ NATURAL TOKEN(NATURAL) COLUMN TOKEN(COLUMN) CREATE TOKEN(CREATE) DELETE TOKEN(DELETE) +EXISTS TOKEN(EXISTS) HAVING TOKEN(HAVING) IMPORT TOKEN(IMPORT) INSERT TOKEN(INSERT) @@ -106,6 +107,7 @@ TBL TOKEN(TBL) TOP TOKEN(TOP) AS TOKEN(AS) BY TOKEN(BY) +IF TOKEN(IF) IN TOKEN(IN) IS TOKEN(IS) ON TOKEN(ON) diff --git a/src/parser/sql_keywords.txt b/src/parser/sql_keywords.txt index 4c8821d..312ef4f 100644 --- a/src/parser/sql_keywords.txt +++ b/src/parser/sql_keywords.txt @@ -33,6 +33,8 @@ CREATE TABLE DATABASE INDEX +IF +EXISTS // Import statement IMPORT diff --git a/test/valid_queries.sql b/test/valid_queries.sql index 801f0ad..626c555 100644 --- a/test/valid_queries.sql +++ b/test/valid_queries.sql @@ -11,5 +11,6 @@ SELECT * FROM t1 UNION (SELECT * FROM t2) ORDER BY col1; SELECT * FROM t1 UNION (SELECT * FROM t2 UNION SELECT * FROM t3) ORDER BY col1; # CREATE statement CREATE TABLE "table" FROM TBL FILE 'students.tbl' +CREATE TABLE IF NOT EXISTS "table" FROM TBL FILE 'students.tbl' # Multiple statements CREATE TABLE "table" FROM TBL FILE 'students.tbl'; SELECT * FROM "table"; \ No newline at end of file