diff --git a/src/Parsers/ExpressionElementParsers.cpp b/src/Parsers/ExpressionElementParsers.cpp index 7c82c4aca1e..a71dbf153cb 100644 --- a/src/Parsers/ExpressionElementParsers.cpp +++ b/src/Parsers/ExpressionElementParsers.cpp @@ -261,10 +261,12 @@ bool ParserFunction::parseImpl(Pos & pos, ASTPtr & node, Expected & expected) { ParserIdentifier id_parser; ParserKeyword distinct("DISTINCT"); + ParserKeyword all("ALL"); ParserExpressionList contents(false); ParserSelectWithUnionQuery select; ParserKeyword over("OVER"); + bool has_all = false; bool has_distinct_modifier = false; ASTPtr identifier; @@ -279,10 +281,19 @@ bool ParserFunction::parseImpl(Pos & pos, ASTPtr & node, Expected & expected) return false; ++pos; + if (all.ignore(pos, expected)) + has_all = true; if (distinct.ignore(pos, expected)) has_distinct_modifier = true; - else + + if (!has_all && all.ignore(pos, expected)) + has_all = true; + + if (has_all && has_distinct_modifier) + throw Exception("Can not use DISTINCT alongside ALL", ErrorCodes::SYNTAX_ERROR); + + if (!has_distinct_modifier) { auto old_pos = pos; auto maybe_an_subquery = pos->type == TokenType::OpeningRoundBracket; @@ -356,9 +367,18 @@ bool ParserFunction::parseImpl(Pos & pos, ASTPtr & node, Expected & expected) expr_list_params = expr_list_args; expr_list_args = nullptr; + if (all.ignore(pos, expected)) + has_all = true; + if (distinct.ignore(pos, expected)) has_distinct_modifier = true; + if (!has_all && all.ignore(pos, expected)) + has_all = true; + + if (has_all && has_distinct_modifier) + throw Exception("Can not use DISTINCT alongside ALL", ErrorCodes::SYNTAX_ERROR); + if (!contents.parse(pos, expr_list_args, expected)) return false; diff --git a/src/Parsers/ExpressionListParsers.cpp b/src/Parsers/ExpressionListParsers.cpp index 6e169e9135c..4ee1128c2ef 100644 --- a/src/Parsers/ExpressionListParsers.cpp +++ b/src/Parsers/ExpressionListParsers.cpp @@ -87,9 +87,6 @@ bool ParserList::parseImpl(Pos & pos, ASTPtr & node, Expected & expected) auto parse_element = [&] { - ParserKeyword all("ALL"); - all.ignore(pos, expected); - ASTPtr element; if (!elem_parser->parse(pos, element, expected)) return false; diff --git a/src/Parsers/ParserSelectQuery.cpp b/src/Parsers/ParserSelectQuery.cpp index b1c07a777c9..c72264cc001 100644 --- a/src/Parsers/ParserSelectQuery.cpp +++ b/src/Parsers/ParserSelectQuery.cpp @@ -21,7 +21,7 @@ namespace ErrorCodes extern const int LIMIT_BY_WITH_TIES_IS_NOT_SUPPORTED; extern const int ROW_AND_ROWS_TOGETHER; extern const int FIRST_AND_NEXT_TOGETHER; - extern const int LOGICAL_ERROR; + extern const int SYNTAX_ERROR; } @@ -109,7 +109,7 @@ bool ParserSelectQuery::parseImpl(Pos & pos, ASTPtr & node, Expected & expected) has_all = true; if (has_all && select_query->distinct) - throw Exception("Can not use DISTINCT alongside ALL", ErrorCodes::LOGICAL_ERROR); + throw Exception("Can not use DISTINCT alongside ALL", ErrorCodes::SYNTAX_ERROR); if (s_top.ignore(pos, expected)) { diff --git a/tests/queries/0_stateless/01632_select_all_syntax.reference b/tests/queries/0_stateless/01632_select_all_syntax.reference index 47c2a8c9b59..3fad8c33238 100644 --- a/tests/queries/0_stateless/01632_select_all_syntax.reference +++ b/tests/queries/0_stateless/01632_select_all_syntax.reference @@ -5,3 +5,6 @@ a 2 45 45 +45 +2 +1 diff --git a/tests/queries/0_stateless/01632_select_all_syntax.sql b/tests/queries/0_stateless/01632_select_all_syntax.sql index 9415f5ef0c7..42fd63bc290 100644 --- a/tests/queries/0_stateless/01632_select_all_syntax.sql +++ b/tests/queries/0_stateless/01632_select_all_syntax.sql @@ -2,8 +2,14 @@ SELECT ALL 'a'; SELECT DISTINCT 'a'; SELECT ALL * FROM (SELECT 1 UNION ALL SELECT 1); SELECT DISTINCT * FROM (SELECT 2 UNION ALL SELECT 2); -SELECT ALL DISTINCT 1; -- { clientError 49 } -SELECT DISTINCT ALL 1; -- { clientError 49 } +SELECT ALL DISTINCT 1; -- { clientError 62 } +SELECT DISTINCT ALL 1; -- { clientError 62 } SELECT sum(number) FROM numbers(10); SELECT sum(ALL number) FROM numbers(10); +SELECT sum(DISTINCT number) FROM numbers(10); + +SELECT sum(ALL x) FROM (SELECT 1 x UNION ALL SELECT 1); +SELECT sum(DISTINCT x) FROM (SELECT 1 x UNION ALL SELECT 1); +SELECT sum(ALL DISTINCT x) FROM (SELECT 1 x UNION ALL SELECT 1); -- { clientError 62 } +SELECT sum(DISTINCT ALL x) FROM (SELECT 1 x UNION ALL SELECT 1); -- { clientError 62 }