2019-01-30 02:47:26 +00:00
|
|
|
#include <Interpreters/FindIdentifierBestTableVisitor.h>
|
|
|
|
#include <Interpreters/IdentifierSemantic.h>
|
|
|
|
|
|
|
|
|
|
|
|
namespace DB
|
|
|
|
{
|
|
|
|
|
2019-02-26 10:07:58 +00:00
|
|
|
FindIdentifierBestTableData::FindIdentifierBestTableData(const std::vector<TableWithColumnNames> & tables_)
|
2019-01-30 02:47:26 +00:00
|
|
|
: tables(tables_)
|
|
|
|
{
|
|
|
|
}
|
|
|
|
|
|
|
|
void FindIdentifierBestTableData::visit(ASTIdentifier & identifier, ASTPtr &)
|
|
|
|
{
|
|
|
|
const DatabaseAndTableWithAlias * best_table = nullptr;
|
|
|
|
|
|
|
|
if (!identifier.compound())
|
|
|
|
{
|
2019-03-04 15:53:51 +00:00
|
|
|
for (const auto & table_names : tables)
|
2019-02-26 10:07:58 +00:00
|
|
|
{
|
2019-03-04 15:53:51 +00:00
|
|
|
if (std::find(table_names.second.begin(), table_names.second.end(), identifier.name) != table_names.second.end())
|
2019-02-26 10:07:58 +00:00
|
|
|
{
|
|
|
|
// TODO: make sure no collision ever happens
|
|
|
|
if (!best_table)
|
2019-03-04 15:53:51 +00:00
|
|
|
best_table = &table_names.first;
|
2019-02-26 10:07:58 +00:00
|
|
|
}
|
|
|
|
}
|
2019-01-30 02:47:26 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2019-02-26 10:07:58 +00:00
|
|
|
// FIXME: make a better matcher using `names`?
|
2019-01-30 02:47:26 +00:00
|
|
|
size_t best_match = 0;
|
2019-03-04 15:53:51 +00:00
|
|
|
for (const auto & table_names : tables)
|
2019-01-30 02:47:26 +00:00
|
|
|
{
|
2019-03-04 15:53:51 +00:00
|
|
|
if (size_t match = IdentifierSemantic::canReferColumnToTable(identifier, table_names.first))
|
2019-01-30 02:47:26 +00:00
|
|
|
if (match > best_match)
|
|
|
|
{
|
|
|
|
best_match = match;
|
2019-03-04 15:53:51 +00:00
|
|
|
best_table = &table_names.first;
|
2019-01-30 02:47:26 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
identifier_table.emplace_back(&identifier, best_table);
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|