From b887ec8e98cf3fbeaf418aa799e78b64c9b86c3c Mon Sep 17 00:00:00 2001 From: zhang2014 Date: Tue, 25 Sep 2018 10:42:51 +0800 Subject: [PATCH] ISSUES-3145 support qualified asterisk --- dbms/src/Interpreters/ExpressionAnalyzer.cpp | 53 +++++++++----------- dbms/src/Interpreters/QueryNormalizer.cpp | 8 +-- 2 files changed, 29 insertions(+), 32 deletions(-) diff --git a/dbms/src/Interpreters/ExpressionAnalyzer.cpp b/dbms/src/Interpreters/ExpressionAnalyzer.cpp index 20ffb4dda0..1924608b67 100644 --- a/dbms/src/Interpreters/ExpressionAnalyzer.cpp +++ b/dbms/src/Interpreters/ExpressionAnalyzer.cpp @@ -281,26 +281,36 @@ ExpressionAnalyzer::ExpressionAnalyzer( analyzeAggregation(); } -void ExpressionAnalyzer::translateQualifiedNames() +static std::vector getTableExpressions(const ASTPtr & query) { - if (!select_query || !select_query->tables || select_query->tables->children.empty()) - return; + ASTSelectQuery * select_query = typeid_cast(query.get()); - auto & element = static_cast(*select_query->tables->children[0]); + std::vector tables_expression; - if (!element.table_expression) /// This is ARRAY JOIN without a table at the left side. - return; + if (select_query && select_query->tables) + { + for (const auto & element : select_query->tables->children) + { + ASTTablesInSelectQueryElement & select_element = static_cast(*element); - auto & table_expression = static_cast(*element.table_expression); - auto * join = select_query->join(); + if (select_element.table_expression) + tables_expression.emplace_back(static_cast(*select_element.table_expression)); + } + } - std::vector tables = {getTableNameWithAliasFromTableExpression(table_expression, context)}; + return tables_expression; +} - if (join) - { - const auto & join_table_expression = static_cast(*join->table_expression); - tables.emplace_back(getTableNameWithAliasFromTableExpression(join_table_expression, context)); - } +void ExpressionAnalyzer::translateQualifiedNames() +{ + if (!select_query || !select_query->tables || select_query->tables->children.empty()) + return; + + std::vector tables; + std::vector tables_expression = getTableExpressions(query); + + for (const auto & table_expression : tables_expression) + tables.emplace_back(getTableNameWithAliasFromTableExpression(table_expression, context)); translateQualifiedNamesImpl(query, tables); } @@ -863,18 +873,6 @@ static NamesAndTypesList::iterator findColumn(const String & name, NamesAndTypes [&](const NamesAndTypesList::value_type & val) { return val.name == name; }); } -static void getTableExpressions(const ASTPtr & node, std::vector & table_expressions) -{ - if (ASTTableExpression * table_expression = typeid_cast(node.get())) - { - table_expressions.emplace_back(*table_expression); - return; - } - - for (const auto & child : node->children) - getTableExpressions(child, table_expressions); -} - static NamesAndTypesList getNamesAndTypeListFromTableExpression(const ASTTableExpression & table_expression, const Context & context) { NamesAndTypesList names_and_type_list; @@ -920,8 +918,7 @@ void ExpressionAnalyzer::normalizeTree() TableNamesAndColumnsName table_names_nad_columns_name; if (select_query && select_query->tables && !select_query->tables->children.empty()) { - std::vector tables_expression; - getTableExpressions(select_query->tables, tables_expression); + std::vector tables_expression = getTableExpressions(query); for (const auto & table_expression : tables_expression) { diff --git a/dbms/src/Interpreters/QueryNormalizer.cpp b/dbms/src/Interpreters/QueryNormalizer.cpp index f1effab2e7..0d056e8219 100644 --- a/dbms/src/Interpreters/QueryNormalizer.cpp +++ b/dbms/src/Interpreters/QueryNormalizer.cpp @@ -147,7 +147,7 @@ void QueryNormalizer::performImpl(ASTPtr & ast, MapOfASTs & finished_asts, SetOf } else if (ASTExpressionList * expr_list = typeid_cast(ast.get())) { - /// Replace * with a list of columns. + /// Replace *, alias.*, database.table.* with a list of columns. ASTs & asts = expr_list->children; for (int i = static_cast(asts.size()) - 1; i >= 0; --i) { @@ -164,10 +164,10 @@ void QueryNormalizer::performImpl(ASTPtr & ast, MapOfASTs & finished_asts, SetOf ASTIdentifier * identifier = typeid_cast(qualified_asterisk->children[0].get()); size_t num_components = identifier->children.size(); - for (const auto table_name_and_names : table_names_and_columns_name) + for (const auto table_name_and_columns_name : table_names_and_columns_name) { - const auto table_name = table_name_and_names.first; - const auto table_all_columns_name = table_name_and_names.second; + const auto table_name = table_name_and_columns_name.first; + const auto table_all_columns_name = table_name_and_columns_name.second; if ((num_components == 2 && !table_name.database.empty() -- GitLab