mirror of
https://github.com/ClickHouse/ClickHouse.git
synced 2024-11-24 16:42:05 +00:00
fix several cases, while reading subcolumns
This commit is contained in:
parent
fe6b964b32
commit
ac3de63a71
@ -546,7 +546,7 @@ ColumnPtr DataTypeNullable::getSubcolumn(const String & subcolumn_name, const IC
|
||||
{
|
||||
const auto & column_nullable = assert_cast<const ColumnNullable &>(column);
|
||||
if (subcolumn_name == "null")
|
||||
return column_nullable.getNullMapColumnPtr()->assumeMutable();
|
||||
return column_nullable.getNullMapColumnPtr();
|
||||
|
||||
return nested_data_type->getSubcolumn(subcolumn_name, column_nullable.getNestedColumn());
|
||||
}
|
||||
|
@ -331,8 +331,7 @@ NamesAndTypesList ColumnsDescription::getAll() const
|
||||
|
||||
bool ColumnsDescription::has(const String & column_name) const
|
||||
{
|
||||
return columns.get<1>().find(column_name) != columns.get<1>().end()
|
||||
|| subcolumns.find(column_name) != subcolumns.end();
|
||||
return columns.get<1>().find(column_name) != columns.get<1>().end();
|
||||
}
|
||||
|
||||
bool ColumnsDescription::hasNested(const String & column_name) const
|
||||
@ -341,6 +340,16 @@ bool ColumnsDescription::hasNested(const String & column_name) const
|
||||
return range.first != range.second && range.first->name.length() > column_name.length();
|
||||
}
|
||||
|
||||
bool ColumnsDescription::hasSubcolumn(const String & column_name) const
|
||||
{
|
||||
return subcolumns.find(column_name) != subcolumns.end();
|
||||
}
|
||||
|
||||
bool ColumnsDescription::hasInStorageOrSubcolumn(const String & column_name) const
|
||||
{
|
||||
return has(column_name) || hasSubcolumn(column_name);
|
||||
}
|
||||
|
||||
const ColumnDescription & ColumnsDescription::get(const String & column_name) const
|
||||
{
|
||||
auto it = columns.get<1>().find(column_name);
|
||||
|
@ -85,6 +85,8 @@ public:
|
||||
|
||||
bool has(const String & column_name) const;
|
||||
bool hasNested(const String & column_name) const;
|
||||
bool hasSubcolumn(const String & column_name) const;
|
||||
bool hasInStorageOrSubcolumn(const String & column_name) const;
|
||||
const ColumnDescription & get(const String & column_name) const;
|
||||
|
||||
template <typename F>
|
||||
|
@ -879,6 +879,8 @@ void IMergeTreeDataPart::loadColumns(bool require)
|
||||
{
|
||||
String path = getFullRelativePath() + "columns.txt";
|
||||
auto metadata_snapshot = storage.getInMemoryMetadataPtr();
|
||||
NamesAndTypesList loaded_columns;
|
||||
|
||||
if (!volume->getDisk()->exists(path))
|
||||
{
|
||||
/// We can get list of columns only from columns.txt in compact parts.
|
||||
@ -888,25 +890,23 @@ void IMergeTreeDataPart::loadColumns(bool require)
|
||||
/// If there is no file with a list of columns, write it down.
|
||||
for (const NameAndTypePair & column : metadata_snapshot->getColumns().getAllPhysical())
|
||||
if (volume->getDisk()->exists(getFullRelativePath() + getFileNameForColumn(column) + ".bin"))
|
||||
columns.push_back(column);
|
||||
loaded_columns.push_back(column);
|
||||
|
||||
if (columns.empty())
|
||||
throw Exception("No columns in part " + name, ErrorCodes::NO_FILE_IN_DATA_PART);
|
||||
|
||||
{
|
||||
auto buf = volume->getDisk()->writeFile(path + ".tmp", 4096);
|
||||
columns.writeText(*buf);
|
||||
loaded_columns.writeText(*buf);
|
||||
}
|
||||
volume->getDisk()->moveFile(path + ".tmp", path);
|
||||
}
|
||||
else
|
||||
{
|
||||
columns.readText(*volume->getDisk()->readFile(path));
|
||||
loaded_columns.readText(*volume->getDisk()->readFile(path));
|
||||
}
|
||||
|
||||
size_t pos = 0;
|
||||
for (const auto & column : columns)
|
||||
column_name_to_position.emplace(column.name, pos++);
|
||||
setColumns(loaded_columns);
|
||||
}
|
||||
|
||||
bool IMergeTreeDataPart::shallParticipateInMerges(const StoragePolicyPtr & storage_policy) const
|
||||
|
16
tests/queries/0_stateless/01475_read_subcolumns_3.reference
Normal file
16
tests/queries/0_stateless/01475_read_subcolumns_3.reference
Normal file
@ -0,0 +1,16 @@
|
||||
Nullable
|
||||
2
|
||||
2
|
||||
2
|
||||
2
|
||||
Map
|
||||
2
|
||||
2
|
||||
2
|
||||
2
|
||||
2
|
||||
2
|
||||
1 2
|
||||
2 2
|
||||
3 3
|
||||
1
|
39
tests/queries/0_stateless/01475_read_subcolumns_3.sql
Normal file
39
tests/queries/0_stateless/01475_read_subcolumns_3.sql
Normal file
@ -0,0 +1,39 @@
|
||||
DROP TABLE IF EXISTS null_subcolumns;
|
||||
|
||||
SELECT 'Nullable';
|
||||
CREATE TABLE null_subcolumns (id UInt32, n Nullable(String)) ENGINE = MergeTree ORDER BY id;
|
||||
|
||||
INSERT INTO null_subcolumns VALUES (1, 'foo') (2, NULL) (3, NULL) (4, 'abc');
|
||||
|
||||
SELECT count() FROM null_subcolumns WHERE n.null;
|
||||
SELECT count() FROM null_subcolumns PREWHERE n.null;
|
||||
|
||||
-- Check, that subcolumns will be available after restart.
|
||||
DETACH TABLE null_subcolumns;
|
||||
ATTACH TABLE null_subcolumns;
|
||||
|
||||
SELECT count() FROM null_subcolumns WHERE n.null;
|
||||
SELECT count() FROM null_subcolumns PREWHERE n.null;
|
||||
|
||||
DROP TABLE null_subcolumns;
|
||||
DROP TABLE IF EXISTS map_subcolumns;
|
||||
|
||||
SELECT 'Map';
|
||||
SET allow_experimental_map_type = 1;
|
||||
CREATE TABLE map_subcolumns (id UInt32, m Map(String, UInt32)) ENGINE = MergeTree ORDER BY id;
|
||||
INSERT INTO map_subcolumns VALUES (1, map('a', 1, 'b', 2)) (2, map('a', 3, 'c', 4)), (3, map('b', 5, 'c', 6, 'd', 7));
|
||||
|
||||
SELECT count() FROM map_subcolumns WHERE has(m.keys, 'a');
|
||||
SELECT count() FROM map_subcolumns PREWHERE has(m.keys, 'b');
|
||||
|
||||
SELECT count() FROM map_subcolumns WHERE arrayMax(m.values) > 3;
|
||||
SELECT count() FROM map_subcolumns PREWHERE arrayMax(m.values) > 3;
|
||||
|
||||
DETACH TABLE map_subcolumns;
|
||||
ATTACH TABLE map_subcolumns;
|
||||
|
||||
SELECT count() FROM map_subcolumns WHERE has(m.keys, 'a');
|
||||
SELECT count() FROM map_subcolumns PREWHERE has(m.keys, 'b');
|
||||
|
||||
SELECT id, m.size0 FROM map_subcolumns;
|
||||
SELECT count() FROM map_subcolumns WHERE m.size0 > 2;
|
Loading…
Reference in New Issue
Block a user