Skip to content

Commit a6a1e74

Browse files
committed
Support SHOW TABLES
1 parent 231370a commit a6a1e74

File tree

3 files changed

+140
-12
lines changed

3 files changed

+140
-12
lines changed

src/ast/mod.rs

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1012,6 +1012,15 @@ pub enum Statement {
10121012
table_name: ObjectName,
10131013
filter: Option<ShowStatementFilter>,
10141014
},
1015+
/// SHOW TABLES
1016+
///
1017+
/// Note: this is a MySQL-specific statement.
1018+
ShowTables {
1019+
extended: bool,
1020+
full: bool,
1021+
db_name: Option<Ident>,
1022+
filter: Option<ShowStatementFilter>,
1023+
},
10151024
/// `{ BEGIN [ TRANSACTION | WORK ] | START TRANSACTION } ...`
10161025
StartTransaction { modes: Vec<TransactionMode> },
10171026
/// `SET TRANSACTION ...`
@@ -1814,6 +1823,26 @@ impl fmt::Display for Statement {
18141823
}
18151824
Ok(())
18161825
}
1826+
Statement::ShowTables {
1827+
extended,
1828+
full,
1829+
db_name,
1830+
filter,
1831+
} => {
1832+
write!(
1833+
f,
1834+
"SHOW {extended}{full}TABLES",
1835+
extended = if *extended { "EXTENDED " } else { "" },
1836+
full = if *full { "FULL " } else { "" },
1837+
)?;
1838+
if let Some(db_name) = db_name {
1839+
write!(f, " FROM {}", db_name)?;
1840+
}
1841+
if let Some(filter) = filter {
1842+
write!(f, " {}", filter)?;
1843+
}
1844+
Ok(())
1845+
}
18171846
Statement::StartTransaction { modes } => {
18181847
write!(f, "START TRANSACTION")?;
18191848
if !modes.is_empty() {

src/parser.rs

Lines changed: 33 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -3681,17 +3681,19 @@ impl<'a> Parser<'a> {
36813681
}
36823682

36833683
pub fn parse_show(&mut self) -> Result<Statement, ParserError> {
3684+
let extended = self.parse_keyword(Keyword::EXTENDED);
3685+
let full = self.parse_keyword(Keyword::FULL);
36843686
if self
3685-
.parse_one_of_keywords(&[
3686-
Keyword::EXTENDED,
3687-
Keyword::FULL,
3688-
Keyword::COLUMNS,
3689-
Keyword::FIELDS,
3690-
])
3687+
.parse_one_of_keywords(&[Keyword::COLUMNS, Keyword::FIELDS])
36913688
.is_some()
36923689
{
3693-
self.prev_token();
3694-
Ok(self.parse_show_columns()?)
3690+
Ok(self.parse_show_columns(extended, full)?)
3691+
} else if self.parse_keyword(Keyword::TABLES) {
3692+
Ok(self.parse_show_tables(extended, full)?)
3693+
} else if extended || full {
3694+
Err(ParserError::ParserError(
3695+
"EXTENDED/FULL are not supported with this type of SHOW query".to_string(),
3696+
))
36953697
} else if self.parse_one_of_keywords(&[Keyword::CREATE]).is_some() {
36963698
Ok(self.parse_show_create()?)
36973699
} else {
@@ -3727,10 +3729,11 @@ impl<'a> Parser<'a> {
37273729
Ok(Statement::ShowCreate { obj_type, obj_name })
37283730
}
37293731

3730-
pub fn parse_show_columns(&mut self) -> Result<Statement, ParserError> {
3731-
let extended = self.parse_keyword(Keyword::EXTENDED);
3732-
let full = self.parse_keyword(Keyword::FULL);
3733-
self.expect_one_of_keywords(&[Keyword::COLUMNS, Keyword::FIELDS])?;
3732+
pub fn parse_show_columns(
3733+
&mut self,
3734+
extended: bool,
3735+
full: bool,
3736+
) -> Result<Statement, ParserError> {
37343737
self.expect_one_of_keywords(&[Keyword::FROM, Keyword::IN])?;
37353738
let table_name = self.parse_object_name()?;
37363739
// MySQL also supports FROM <database> here. In other words, MySQL
@@ -3745,6 +3748,24 @@ impl<'a> Parser<'a> {
37453748
})
37463749
}
37473750

3751+
pub fn parse_show_tables(
3752+
&mut self,
3753+
extended: bool,
3754+
full: bool,
3755+
) -> Result<Statement, ParserError> {
3756+
let db_name = match self.parse_one_of_keywords(&[Keyword::FROM, Keyword::IN]) {
3757+
Some(_) => Some(self.parse_identifier()?),
3758+
None => None,
3759+
};
3760+
let filter = self.parse_show_statement_filter()?;
3761+
Ok(Statement::ShowTables {
3762+
extended,
3763+
full,
3764+
db_name,
3765+
filter,
3766+
})
3767+
}
3768+
37483769
pub fn parse_show_statement_filter(
37493770
&mut self,
37503771
) -> Result<Option<ShowStatementFilter>, ParserError> {

tests/sqlparser_mysql.rs

Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -118,6 +118,84 @@ fn parse_show_columns() {
118118
}
119119
}
120120

121+
#[test]
122+
fn parse_show_tables() {
123+
assert_eq!(
124+
mysql_and_generic().verified_stmt("SHOW TABLES"),
125+
Statement::ShowTables {
126+
extended: false,
127+
full: false,
128+
db_name: None,
129+
filter: None,
130+
}
131+
);
132+
assert_eq!(
133+
mysql_and_generic().verified_stmt("SHOW TABLES FROM mydb"),
134+
Statement::ShowTables {
135+
extended: false,
136+
full: false,
137+
db_name: Some(Ident::new("mydb")),
138+
filter: None,
139+
}
140+
);
141+
assert_eq!(
142+
mysql_and_generic().verified_stmt("SHOW EXTENDED TABLES"),
143+
Statement::ShowTables {
144+
extended: true,
145+
full: false,
146+
db_name: None,
147+
filter: None,
148+
}
149+
);
150+
assert_eq!(
151+
mysql_and_generic().verified_stmt("SHOW FULL TABLES"),
152+
Statement::ShowTables {
153+
extended: false,
154+
full: true,
155+
db_name: None,
156+
filter: None,
157+
}
158+
);
159+
assert_eq!(
160+
mysql_and_generic().verified_stmt("SHOW TABLES LIKE 'pattern'"),
161+
Statement::ShowTables {
162+
extended: false,
163+
full: false,
164+
db_name: None,
165+
filter: Some(ShowStatementFilter::Like("pattern".into())),
166+
}
167+
);
168+
assert_eq!(
169+
mysql_and_generic().verified_stmt("SHOW TABLES WHERE 1 = 2"),
170+
Statement::ShowTables {
171+
extended: false,
172+
full: false,
173+
db_name: None,
174+
filter: Some(ShowStatementFilter::Where(
175+
mysql_and_generic().verified_expr("1 = 2")
176+
)),
177+
}
178+
);
179+
mysql_and_generic().one_statement_parses_to("SHOW TABLES IN mydb", "SHOW TABLES FROM mydb");
180+
}
181+
182+
#[test]
183+
fn parse_show_extended_full() {
184+
assert!(mysql_and_generic()
185+
.parse_sql_statements("SHOW EXTENDED FULL TABLES")
186+
.is_ok());
187+
assert!(mysql_and_generic()
188+
.parse_sql_statements("SHOW EXTENDED FULL COLUMNS FROM mytable")
189+
.is_ok());
190+
// SHOW EXTENDED/FULL can only be used with COLUMNS and TABLES
191+
assert!(mysql_and_generic()
192+
.parse_sql_statements("SHOW EXTENDED FULL CREATE TABLE mytable")
193+
.is_err());
194+
assert!(mysql_and_generic()
195+
.parse_sql_statements("SHOW EXTENDED FULL CREATE TABLE mytable")
196+
.is_err());
197+
}
198+
121199
#[test]
122200
fn parse_show_create() {
123201
let obj_name = ObjectName(vec![Ident::new("myident")]);

0 commit comments

Comments
 (0)