@@ -156,29 +156,6 @@ impl Parser {
156
156
Ok ( expr)
157
157
}
158
158
159
- /// Parse expression for DEFAULT clause in CREATE TABLE
160
- pub fn parse_default_expr ( & mut self , precedence : u8 ) -> Result < ASTNode , ParserError > {
161
- debug ! ( "parsing expr" ) ;
162
- let mut expr = self . parse_prefix ( ) ?;
163
- debug ! ( "prefix: {:?}" , expr) ;
164
- loop {
165
- // stop parsing on `NULL` | `NOT NULL`
166
- match self . peek_token ( ) {
167
- Some ( Token :: SQLWord ( ref k) ) if k. keyword == "NOT" || k. keyword == "NULL" => break ,
168
- _ => { }
169
- }
170
-
171
- let next_precedence = self . get_next_precedence ( ) ?;
172
- debug ! ( "next precedence: {:?}" , next_precedence) ;
173
- if precedence >= next_precedence {
174
- break ;
175
- }
176
-
177
- expr = self . parse_infix ( expr, next_precedence) ?;
178
- }
179
- Ok ( expr)
180
- }
181
-
182
159
/// Parse an expression prefix
183
160
pub fn parse_prefix ( & mut self ) -> Result < ASTNode , ParserError > {
184
161
let tok = self
@@ -896,29 +873,18 @@ impl Parser {
896
873
} else if let Some ( Token :: SQLWord ( column_name) ) = self . peek_token ( ) {
897
874
self . next_token ( ) ;
898
875
let data_type = self . parse_data_type ( ) ?;
899
- let is_primary = self . parse_keywords ( vec ! [ "PRIMARY" , "KEY" ] ) ;
900
- let is_unique = self . parse_keyword ( "UNIQUE" ) ;
901
- let default = if self . parse_keyword ( "DEFAULT" ) {
902
- let expr = self . parse_default_expr ( 0 ) ?;
903
- Some ( expr)
904
- } else {
905
- None
906
- } ;
907
- let allow_null = if self . parse_keywords ( vec ! [ "NOT" , "NULL" ] ) {
908
- false
909
- } else {
910
- let _ = self . parse_keyword ( "NULL" ) ;
911
- true
912
- } ;
913
- debug ! ( "default: {:?}" , default ) ;
876
+ let mut constraints = vec ! [ ] ;
877
+ loop {
878
+ match self . peek_token ( ) {
879
+ None | Some ( Token :: Comma ) | Some ( Token :: RParen ) => break ,
880
+ _ => constraints. push ( self . parse_column_constraint ( ) ?) ,
881
+ }
882
+ }
914
883
915
884
columns. push ( SQLColumnDef {
916
885
name : column_name. as_sql_ident ( ) ,
917
886
data_type,
918
- allow_null,
919
- is_primary,
920
- is_unique,
921
- default,
887
+ constraints,
922
888
} ) ;
923
889
} else {
924
890
return self . expected ( "column name or constraint definition" , self . peek_token ( ) ) ;
@@ -935,6 +901,58 @@ impl Parser {
935
901
Ok ( ( columns, constraints) )
936
902
}
937
903
904
+ pub fn parse_column_constraint ( & mut self ) -> Result < ColumnConstraint , ParserError > {
905
+ if self . parse_keywords ( vec ! [ "NOT" , "NULL" ] ) {
906
+ return Ok ( ColumnConstraint :: NotNull ) ;
907
+ } else if self . parse_keyword ( "NULL" ) {
908
+ return Ok ( ColumnConstraint :: Null ) ;
909
+ } else if self . parse_keyword ( "DEFAULT" ) {
910
+ // We want to allow as many DEFAULT expressions as possible, but
911
+ // calling self.parse_expr() will choke on expressions like "DEFAULT
912
+ // 1 NOT NULL". Typically this would be a syntax error, as "1 NOT
913
+ // NULL" is not a valid SQL expression, but in this case we know
914
+ // that NOT NULL is part of the next column constraint. As it turns
915
+ // out, the only expressions that cause trouble all have precedence
916
+ // less than or equal to BETWEEN, so we pass BETWEEN_PREC to stop
917
+ // parsing on tokens with precedence less than or equal to BETWEEN.
918
+ // The same trick is employed by PostgreSQL [0].
919
+ // https://github.com/postgres/postgres/blob/56b78626c/src/backend/parser/gram.y#L13366-L13370
920
+ let expr = self . parse_subexpr ( Self :: BETWEEN_PREC ) ?;
921
+ return Ok ( ColumnConstraint :: Default ( expr) ) ;
922
+ }
923
+
924
+ let name = if self . parse_keyword ( "CONSTRAINT" ) {
925
+ Some ( self . parse_identifier ( ) ?)
926
+ } else {
927
+ None
928
+ } ;
929
+
930
+ if self . parse_keywords ( vec ! [ "PRIMARY" , "KEY" ] ) {
931
+ Ok ( ColumnConstraint :: Unique {
932
+ name,
933
+ is_primary : true ,
934
+ } )
935
+ } else if self . parse_keyword ( "UNIQUE" ) {
936
+ Ok ( ColumnConstraint :: Unique {
937
+ name,
938
+ is_primary : false ,
939
+ } )
940
+ } else if self . parse_keyword ( "REFERENCES" ) {
941
+ let foreign_table = self . parse_object_name ( ) ?;
942
+ let referred_columns = self . parse_parenthesized_column_list ( Mandatory ) ?;
943
+ Ok ( ColumnConstraint :: ForeignKey {
944
+ name,
945
+ foreign_table,
946
+ referred_columns,
947
+ } )
948
+ } else {
949
+ parser_err ! ( format!(
950
+ "Unexpected token in column definition: {:?}" ,
951
+ self . peek_token( )
952
+ ) )
953
+ }
954
+ }
955
+
938
956
pub fn parse_optional_table_constraint (
939
957
& mut self ,
940
958
) -> Result < Option < TableConstraint > , ParserError > {
0 commit comments