Skip to content

Commit e090712

Browse files
committed
Support MySQL index options in CREATE TABLE and ALTER TABLE
1 parent db2636b commit e090712

File tree

4 files changed

+25
-7
lines changed

4 files changed

+25
-7
lines changed

src/ast/ddl.rs

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1125,6 +1125,8 @@ pub enum TableConstraint {
11251125
index_type: Option<IndexType>,
11261126
/// Referred column identifier list.
11271127
columns: Vec<IndexColumn>,
1128+
/// Optional index options such as `USING`; see [`IndexOption`].
1129+
index_options: Vec<IndexOption>,
11281130
},
11291131
/// MySQLs [fulltext][1] definition. Since the [`SPATIAL`][2] definition is exactly the same,
11301132
/// and MySQL displays both the same way, it is part of this definition as well.
@@ -1253,6 +1255,7 @@ impl fmt::Display for TableConstraint {
12531255
name,
12541256
index_type,
12551257
columns,
1258+
index_options,
12561259
} => {
12571260
write!(f, "{}", if *display_as_key { "KEY" } else { "INDEX" })?;
12581261
if let Some(name) = name {
@@ -1262,7 +1265,9 @@ impl fmt::Display for TableConstraint {
12621265
write!(f, " USING {index_type}")?;
12631266
}
12641267
write!(f, " ({})", display_comma_separated(columns))?;
1265-
1268+
if !index_options.is_empty() {
1269+
write!(f, " {}", display_comma_separated(index_options))?;
1270+
}
12661271
Ok(())
12671272
}
12681273
Self::FulltextOrSpatial {
@@ -1377,12 +1382,16 @@ impl fmt::Display for IndexType {
13771382
}
13781383
}
13791384

1380-
/// MySQLs index option.
1385+
/// MySQL index option, used in [`CREATE TABLE`], [`CREATE INDEX`], and [`ALTER TABLE`].
1386+
///
1387+
/// - `USING { BTREE | HASH }` (note that we permissively parse non-MySQL index types, like `GIN`)
1388+
/// - `COMMENT`: Specifies a comment for the index.
13811389
///
13821390
/// This structure used here [`MySQL` CREATE TABLE][1], [`MySQL` CREATE INDEX][2].
13831391
///
1384-
/// [1]: https://dev.mysql.com/doc/refman/8.3/en/create-table.html
1385-
/// [2]: https://dev.mysql.com/doc/refman/8.3/en/create-index.html
1392+
/// [`CREATE TABLE`]: https://dev.mysql.com/doc/refman/8.4/en/create-table.html
1393+
/// [`CREATE INDEX`]: https://dev.mysql.com/doc/refman/8.4/en/create-index.html
1394+
/// [`ALTER TABLE`]: https://dev.mysql.com/doc/refman/8.4/en/alter-table.html
13861395
#[derive(Debug, Clone, PartialEq, PartialOrd, Eq, Ord, Hash)]
13871396
#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
13881397
#[cfg_attr(feature = "visitor", derive(Visit, VisitMut))]

src/ast/spans.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -713,6 +713,7 @@ impl Spanned for TableConstraint {
713713
name,
714714
index_type: _,
715715
columns,
716+
index_options: _,
716717
} => union_spans(
717718
name.iter()
718719
.map(|i| i.span)

src/parser/mod.rs

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8409,12 +8409,14 @@ impl<'a> Parser<'a> {
84098409

84108410
let index_type = self.parse_optional_using_then_index_type()?;
84118411
let columns = self.parse_parenthesized_index_column_list()?;
8412+
let index_options = self.parse_index_options()?;
84128413

84138414
Ok(Some(TableConstraint::Index {
84148415
display_as_key,
84158416
name,
84168417
index_type,
84178418
columns,
8419+
index_options,
84188420
}))
84198421
}
84208422
Token::Word(w)
@@ -17470,6 +17472,7 @@ mod tests {
1747017472
name: None,
1747117473
index_type: None,
1747217474
columns: vec![mk_expected_col("c1")],
17475+
index_options: vec![],
1747317476
}
1747417477
);
1747517478

@@ -17481,6 +17484,7 @@ mod tests {
1748117484
name: None,
1748217485
index_type: None,
1748317486
columns: vec![mk_expected_col("c1")],
17487+
index_options: vec![],
1748417488
}
1748517489
);
1748617490

@@ -17492,6 +17496,7 @@ mod tests {
1749217496
name: Some(Ident::with_quote('\'', "index")),
1749317497
index_type: None,
1749417498
columns: vec![mk_expected_col("c1"), mk_expected_col("c2")],
17499+
index_options: vec![],
1749517500
}
1749617501
);
1749717502

@@ -17503,6 +17508,7 @@ mod tests {
1750317508
name: None,
1750417509
index_type: Some(IndexType::BTree),
1750517510
columns: vec![mk_expected_col("c1")],
17511+
index_options: vec![],
1750617512
}
1750717513
);
1750817514

@@ -17514,6 +17520,7 @@ mod tests {
1751417520
name: None,
1751517521
index_type: Some(IndexType::Hash),
1751617522
columns: vec![mk_expected_col("c1")],
17523+
index_options: vec![],
1751717524
}
1751817525
);
1751917526

@@ -17525,6 +17532,7 @@ mod tests {
1752517532
name: Some(Ident::new("idx_name")),
1752617533
index_type: Some(IndexType::BTree),
1752717534
columns: vec![mk_expected_col("c1")],
17535+
index_options: vec![],
1752817536
}
1752917537
);
1753017538

@@ -17536,6 +17544,7 @@ mod tests {
1753617544
name: Some(Ident::new("idx_name")),
1753717545
index_type: Some(IndexType::Hash),
1753817546
columns: vec![mk_expected_col("c1")],
17547+
index_options: vec![],
1753917548
}
1754017549
);
1754117550
}

tests/sqlparser_mysql.rs

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4221,9 +4221,8 @@ fn test_ddl_with_index_using() {
42214221
format!("CREATE TABLE foo (name VARCHAR(255), age INT, KEY idx_name {using} {columns})"),
42224222
format!("ALTER TABLE foo ADD KEY idx_name {using} {columns}"),
42234223
format!("CREATE INDEX idx_name ON test{columns} {using}"),
4224-
// TODO: Add index options to `TableConstraint::Index`
4225-
// format!("CREATE TABLE foo (name VARCHAR(255), age INT, KEY idx_name{columns} {using})"),
4226-
// format!("ALTER TABLE foo ADD KEY idx_name{columns} {using}"),
4224+
format!("CREATE TABLE foo (name VARCHAR(255), age INT, KEY idx_name {columns} {using})"),
4225+
format!("ALTER TABLE foo ADD KEY idx_name {columns} {using}"),
42274226
] {
42284227
mysql_and_generic().verified_stmt(&sql);
42294228
}

0 commit comments

Comments
 (0)