aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorEgor Chunaev <egor.chunaev@pinely.com>2023-11-23 18:08:40 +0300
committerrobot-piglet <robot-piglet@yandex-team.com>2023-11-23 18:36:56 +0300
commit1c6a0f0555dad6bcacf5ef2614d7cd88627609f0 (patch)
treef953529aff78e88ec7be727345e0a50bc457d849
parent50c69e8394f3c3e1afef75878953a4c4691d4383 (diff)
downloadydb-1c6a0f0555dad6bcacf5ef2614d7cd88627609f0.tar.gz
Fix serialization of decimal type in TTableSchema
I hereby agree to the terms of the CLA available at: https://yandex.ru/legal/cla/?lang=en Fix for https://github.com/ytsaurus/ytsaurus/issues/173 --- Pull Request resolved: https://github.com/ytsaurus/ytsaurus/pull/174 Co-authored-by: ermolovd <ermolovd@yandex-team.com>
-rw-r--r--yt/cpp/mapreduce/client/skiff.cpp10
-rw-r--r--yt/cpp/mapreduce/interface/common_ut.cpp44
-rw-r--r--yt/cpp/mapreduce/interface/serialize.cpp10
3 files changed, 60 insertions, 4 deletions
diff --git a/yt/cpp/mapreduce/client/skiff.cpp b/yt/cpp/mapreduce/client/skiff.cpp
index ab133e1ae3..1eb2e80d79 100644
--- a/yt/cpp/mapreduce/client/skiff.cpp
+++ b/yt/cpp/mapreduce/client/skiff.cpp
@@ -108,12 +108,18 @@ NSkiff::TSkiffSchemaPtr CreateSkiffSchema(
TVector<TSkiffSchemaPtr> skiffColumns;
for (const auto& column: schema.Columns()) {
TSkiffSchemaPtr skiffColumn;
+ if (column.Deleted().Defined() && *column.Deleted()) {
+ continue;
+ }
if (column.Type() == VT_ANY && *column.TypeV3() != *NTi::Optional(NTi::Yson())) {
// We ignore all complex types until YT-12717 is done.
return nullptr;
}
- if (column.Deleted().Defined() && *column.Deleted()) {
- continue;
+ if (column.TypeV3()->IsDecimal() ||
+ column.TypeV3()->IsOptional() && column.TypeV3()->AsOptional()->GetItemType()->IsDecimal())
+ {
+ // Complex logic for decimal types, ignore them for now.
+ return nullptr;
}
if (column.Required() || NTi::IsSingular(column.TypeV3()->GetTypeName())) {
skiffColumn = CreateSimpleTypeSchema(ValueTypeToSkiffType(column.Type()));
diff --git a/yt/cpp/mapreduce/interface/common_ut.cpp b/yt/cpp/mapreduce/interface/common_ut.cpp
index 3f19433816..f9f0664039 100644
--- a/yt/cpp/mapreduce/interface/common_ut.cpp
+++ b/yt/cpp/mapreduce/interface/common_ut.cpp
@@ -176,6 +176,45 @@ Y_UNIT_TEST_SUITE(Common)
UNIT_ASSERT_EXCEPTION(checkSortBy(schema, {"a", "junk"}), yexception);
}
+ Y_UNIT_TEST(TTableSchema_Decimal)
+ {
+ NYT::TTableSchema tableSchema;
+
+ tableSchema.AddColumn("a", NTi::Decimal(35, 18));
+ tableSchema.AddColumn("b", NTi::Optional(NTi::Decimal(35, 18)));
+ tableSchema.AddColumn("c", NTi::List(NTi::Decimal(35, 18)));
+
+ auto tableSchemaNode = tableSchema.ToNode();
+ const auto& tableSchemaNodeList = tableSchemaNode.AsList();
+
+ // There was a bug in the serialization of decimal type: https://github.com/ytsaurus/ytsaurus/issues/173
+ {
+ const auto& currentType = tableSchemaNodeList[0];
+ UNIT_ASSERT_VALUES_EQUAL(currentType.ChildAsString("type"), "string");
+ UNIT_ASSERT(currentType.ChildAsBool("required"));
+ UNIT_ASSERT(currentType.HasKey("type_v3"));
+ UNIT_ASSERT_VALUES_EQUAL(currentType.At("type_v3").ChildAsString("type_name"), "decimal");
+ }
+ {
+ const auto& currentType = tableSchemaNodeList[1];
+ UNIT_ASSERT_VALUES_EQUAL(currentType.ChildAsString("type"), "string");
+ UNIT_ASSERT(!currentType.ChildAsBool("required"));
+ UNIT_ASSERT(currentType.HasKey("type_v3"));
+ UNIT_ASSERT_VALUES_EQUAL(currentType.At("type_v3").ChildAsString("type_name"), "optional");
+ UNIT_ASSERT_VALUES_EQUAL(currentType.At("type_v3").At("item").ChildAsString("type_name"), "decimal");
+ }
+ {
+ const auto& currentType = tableSchemaNodeList[2];
+ UNIT_ASSERT_VALUES_EQUAL(currentType.ChildAsString("type"), "any");
+ UNIT_ASSERT(currentType.ChildAsBool("required"));
+ UNIT_ASSERT(currentType.HasKey("type_v3"));
+ UNIT_ASSERT_VALUES_EQUAL(currentType.At("type_v3").ChildAsString("type_name"), "list");
+ UNIT_ASSERT_VALUES_EQUAL(currentType.At("type_v3").At("item").ChildAsString("type_name"), "decimal");
+ }
+
+ UNIT_ASSERT_EQUAL(tableSchema, TTableSchema::FromNode(tableSchemaNode));
+ }
+
Y_UNIT_TEST(TColumnSchema_TypeV3)
{
{
@@ -198,6 +237,11 @@ Y_UNIT_TEST_SUITE(Common)
UNIT_ASSERT_VALUES_EQUAL(column.Required(), false);
UNIT_ASSERT_VALUES_EQUAL(column.Type(), VT_ANY);
}
+ {
+ auto column = TColumnSchema().Type(NTi::Decimal(35, 18));
+ UNIT_ASSERT_VALUES_EQUAL(column.Required(), true);
+ UNIT_ASSERT_VALUES_EQUAL(column.Type(), VT_STRING);
+ }
}
Y_UNIT_TEST(ToTypeV3)
diff --git a/yt/cpp/mapreduce/interface/serialize.cpp b/yt/cpp/mapreduce/interface/serialize.cpp
index 7cd8417487..8e701d30b4 100644
--- a/yt/cpp/mapreduce/interface/serialize.cpp
+++ b/yt/cpp/mapreduce/interface/serialize.cpp
@@ -165,10 +165,16 @@ void Serialize(const TColumnSchema& columnSchema, NYson::IYsonConsumer* consumer
.Item("name").Value(columnSchema.Name())
.DoIf(!columnSchema.RawTypeV3().Defined(),
[&] (TFluentMap fluent) {
+ static const auto optionalYson = NTi::Optional(NTi::Yson());
+
fluent.Item("type").Value(NDetail::ToString(columnSchema.Type()));
fluent.Item("required").Value(columnSchema.Required());
- if (columnSchema.Type() == VT_ANY
- && *columnSchema.TypeV3() != *NTi::Optional(NTi::Yson()))
+ if (
+ (columnSchema.Type() == VT_ANY && *columnSchema.TypeV3() != *optionalYson) ||
+ // See https://github.com/ytsaurus/ytsaurus/issues/173
+ columnSchema.TypeV3()->IsDecimal() ||
+ (columnSchema.TypeV3()->IsOptional() && columnSchema.TypeV3()->AsOptional()->GetItemType()->IsDecimal()))
+
{
// A lot of user canonize serialized schema.
// To be backward compatible we only set type_v3 for new types.