This is an automated email from the ASF dual-hosted git repository. eldenmoon pushed a commit to branch branch-2.1 in repository https://gitbox.apache.org/repos/asf/doris.git
The following commit(s) were added to refs/heads/branch-2.1 by this push: new 4cf769b39fb [Improve](table-function) explode json array with json args (#39491) 4cf769b39fb is described below commit 4cf769b39fb60e77630bd3a2d2c8b1309b000e2e Author: amory <wangqian...@selectdb.com> AuthorDate: Tue Aug 27 14:53:17 2024 +0800 [Improve](table-function) explode json array with json args (#39491) --- .../exprs/table_function/vexplode_json_array.cpp | 24 +++- .../vec/exprs/table_function/vexplode_json_array.h | 151 +++++++++++++++++++++ be/src/vec/functions/function_fake.cpp | 52 ++++--- be/src/vec/functions/function_fake.h | 5 + .../generator/ExplodeJsonArrayDouble.java | 2 + .../generator/ExplodeJsonArrayDoubleOuter.java | 2 + .../functions/generator/ExplodeJsonArrayInt.java | 2 + .../generator/ExplodeJsonArrayIntOuter.java | 2 + .../functions/generator/ExplodeJsonArrayJson.java | 2 + .../generator/ExplodeJsonArrayJsonOuter.java | 2 + .../generator/ExplodeJsonArrayString.java | 2 + .../generator/ExplodeJsonArrayStringOuter.java | 2 + .../data/nereids_function_p0/gen_function/gen.out | 41 ++++++ .../table_function/explode_json_array.out | 16 ++- .../nereids_function_p0/gen_function/gen.groovy | 3 + .../table_function/explode_json_array.groovy | 6 +- 16 files changed, 291 insertions(+), 23 deletions(-) diff --git a/be/src/vec/exprs/table_function/vexplode_json_array.cpp b/be/src/vec/exprs/table_function/vexplode_json_array.cpp index 00c4d92a359..3c22ef4e078 100644 --- a/be/src/vec/exprs/table_function/vexplode_json_array.cpp +++ b/be/src/vec/exprs/table_function/vexplode_json_array.cpp @@ -26,6 +26,8 @@ #include <limits> #include "common/status.h" +#include "util/jsonb_parser.h" +#include "util/jsonb_utils.h" #include "vec/columns/column.h" #include "vec/columns/column_nullable.h" #include "vec/columns/columns_number.h" @@ -50,6 +52,7 @@ Status VExplodeJsonArrayTableFunction<DataImpl>::process_init(Block* block, Runt RETURN_IF_ERROR(_expr_context->root()->children()[0]->execute(_expr_context.get(), block, &text_column_idx)); _text_column = block->get_by_position(text_column_idx).column; + _text_datatype = remove_nullable(block->get_by_position(text_column_idx).type); return Status::OK(); } @@ -59,10 +62,20 @@ void VExplodeJsonArrayTableFunction<DataImpl>::process_row(size_t row_idx) { StringRef text = _text_column->get_data_at(row_idx); if (text.data != nullptr) { - rapidjson::Document document; - document.Parse(text.data, text.size); - if (!document.HasParseError() && document.IsArray() && document.GetArray().Size()) { - _cur_size = _parsed_data.set_output(document, document.GetArray().Size()); + if (WhichDataType(_text_datatype).is_json()) { + JsonbDocument* doc = JsonbDocument::createDocument(text.data, text.size); + if (doc && doc->getValue() && doc->getValue()->isArray()) { + auto* a = (ArrayVal*)doc->getValue(); + if (a->numElem() > 0) { + _cur_size = _parsed_data.set_output(*a, a->numElem()); + } + } + } else { + rapidjson::Document document; + document.Parse(text.data, text.size); + if (!document.HasParseError() && document.IsArray() && document.GetArray().Size()) { + _cur_size = _parsed_data.set_output(document, document.GetArray().Size()); + } } } } @@ -70,6 +83,7 @@ void VExplodeJsonArrayTableFunction<DataImpl>::process_row(size_t row_idx) { template <typename DataImpl> void VExplodeJsonArrayTableFunction<DataImpl>::process_close() { _text_column = nullptr; + _text_datatype = nullptr; _parsed_data.reset(); } @@ -141,4 +155,4 @@ template class VExplodeJsonArrayTableFunction<ParsedDataDouble>; template class VExplodeJsonArrayTableFunction<ParsedDataString>; template class VExplodeJsonArrayTableFunction<ParsedDataJSON>; -} // namespace doris::vectorized \ No newline at end of file +} // namespace doris::vectorized diff --git a/be/src/vec/exprs/table_function/vexplode_json_array.h b/be/src/vec/exprs/table_function/vexplode_json_array.h index 1d89d9fa57d..acf31ed40d9 100644 --- a/be/src/vec/exprs/table_function/vexplode_json_array.h +++ b/be/src/vec/exprs/table_function/vexplode_json_array.h @@ -32,6 +32,7 @@ #include "vec/core/types.h" #include "vec/data_types/data_type.h" #include "vec/exprs/table_function/table_function.h" +#include "vec/functions/function_string.h" namespace doris::vectorized { @@ -44,6 +45,7 @@ struct ParsedData { _values_null_flag.clear(); } virtual int set_output(rapidjson::Document& document, int value_size) = 0; + virtual int set_output(ArrayVal& array_doc, int value_size) = 0; virtual void insert_result_from_parsed_data(MutableColumnPtr& column, int64_t cur_offset, int max_step) = 0; virtual void insert_many_same_value_from_parsed_data(MutableColumnPtr& column, @@ -90,6 +92,36 @@ struct ParsedDataInt : public ParsedData<int64_t> { } return value_size; } + int set_output(ArrayVal& array_doc, int value_size) override { + _values_null_flag.resize(value_size, 0); + _backup_data.resize(value_size); + int i = 0; + for (auto& val : array_doc) { + if (val.isInt8()) { + _backup_data[i] = static_cast<const JsonbInt8Val&>(val).val(); + } else if (val.isInt16()) { + _backup_data[i] = static_cast<const JsonbInt16Val&>(val).val(); + } else if (val.isInt32()) { + _backup_data[i] = static_cast<const JsonbInt32Val&>(val).val(); + } else if (val.isInt64()) { + _backup_data[i] = static_cast<const JsonbInt64Val&>(val).val(); + } else if (val.isDouble()) { + auto value = static_cast<const JsonbDoubleVal&>(val).val(); + if (value > MAX_VALUE) { + _backup_data[i] = MAX_VALUE; + } else if (value < MIN_VALUE) { + _backup_data[i] = MIN_VALUE; + } else { + _backup_data[i] = long(value); + } + } else { + _values_null_flag[i] = 1; + _backup_data[i] = 0; + } + ++i; + } + return value_size; + } void insert_result_from_parsed_data(MutableColumnPtr& column, int64_t cur_offset, int max_step) override { @@ -121,6 +153,22 @@ struct ParsedDataDouble : public ParsedData<double> { return value_size; } + int set_output(ArrayVal& array_doc, int value_size) override { + _values_null_flag.resize(value_size, 0); + _backup_data.resize(value_size); + int i = 0; + for (auto& val : array_doc) { + if (val.isDouble()) { + _backup_data[i] = static_cast<const JsonbDoubleVal&>(val).val(); + } else { + _backup_data[i] = 0; + _values_null_flag[i] = 1; + } + ++i; + } + return value_size; + } + void insert_result_from_parsed_data(MutableColumnPtr& column, int64_t cur_offset, int max_step) override { assert_cast<ColumnFloat64*>(column.get()) @@ -220,6 +268,83 @@ struct ParsedDataString : public ParsedDataStringBase { } return value_size; } + + int set_output(ArrayVal& array_doc, int value_size) override { + _data_string_ref.clear(); + _backup_data.clear(); + _values_null_flag.clear(); + int32_t wbytes = 0; + for (auto& val : array_doc) { + switch (val.type()) { + case JsonbType::T_String: { + _backup_data.emplace_back(static_cast<const JsonbStringVal&>(val).getBlob(), + static_cast<const JsonbStringVal&>(val).getBlobLen()); + _values_null_flag.emplace_back(false); + break; + // do not set _data_string here. + // Because the address of the string stored in `_backup_data` may + // change each time `emplace_back()` is called. + } + case JsonbType::T_Int8: { + wbytes = snprintf(tmp_buf, sizeof(tmp_buf), "%d", + static_cast<const JsonbInt8Val&>(val).val()); + _backup_data.emplace_back(tmp_buf, wbytes); + _values_null_flag.emplace_back(false); + break; + } + case JsonbType::T_Int16: { + wbytes = snprintf(tmp_buf, sizeof(tmp_buf), "%d", + static_cast<const JsonbInt16Val&>(val).val()); + _backup_data.emplace_back(tmp_buf, wbytes); + _values_null_flag.emplace_back(false); + break; + } + case JsonbType::T_Int64: { + wbytes = snprintf(tmp_buf, sizeof(tmp_buf), "%" PRId64, + static_cast<const JsonbInt64Val&>(val).val()); + _backup_data.emplace_back(tmp_buf, wbytes); + _values_null_flag.emplace_back(false); + break; + } + case JsonbType::T_Double: { + wbytes = snprintf(tmp_buf, sizeof(tmp_buf), "%f", + static_cast<const JsonbDoubleVal&>(val).val()); + _backup_data.emplace_back(tmp_buf, wbytes); + _values_null_flag.emplace_back(false); + break; + } + case JsonbType::T_Int32: { + wbytes = snprintf(tmp_buf, sizeof(tmp_buf), "%d", + static_cast<const JsonbInt32Val&>(val).val()); + _backup_data.emplace_back(tmp_buf, wbytes); + _values_null_flag.emplace_back(false); + break; + } + case JsonbType::T_True: + _backup_data.emplace_back(TRUE_VALUE); + _values_null_flag.emplace_back(false); + break; + case JsonbType::T_False: + _backup_data.emplace_back(FALSE_VALUE); + _values_null_flag.emplace_back(false); + break; + case JsonbType::T_Null: + _backup_data.emplace_back(); + _values_null_flag.emplace_back(true); + break; + default: + _backup_data.emplace_back(); + _values_null_flag.emplace_back(true); + break; + } + } + // Must set _data_string at the end, so that we can + // save the real addr of string in `_backup_data` to `_data_string`. + for (auto& str : _backup_data) { + _data_string_ref.emplace_back(str.data(), str.length()); + } + return value_size; + } }; struct ParsedDataJSON : public ParsedDataStringBase { @@ -246,6 +371,31 @@ struct ParsedDataJSON : public ParsedDataStringBase { } return value_size; } + + int set_output(ArrayVal& array_doc, int value_size) override { + _data_string_ref.clear(); + _backup_data.clear(); + _values_null_flag.clear(); + auto writer = std::make_unique<JsonbWriter>(); + for (auto& v : array_doc) { + if (v.isObject()) { + writer->reset(); + writer->writeValue(&v); + _backup_data.emplace_back(writer->getOutput()->getBuffer(), + writer->getOutput()->getSize()); + _values_null_flag.emplace_back(false); + } else { + _backup_data.emplace_back(); + _values_null_flag.emplace_back(true); + } + } + // Must set _data_string at the end, so that we can + // save the real addr of string in `_backup_data` to `_data_string`. + for (auto& str : _backup_data) { + _data_string_ref.emplace_back(str); + } + return value_size; + } }; template <typename DataImpl> @@ -267,6 +417,7 @@ private: void _insert_values_into_column(MutableColumnPtr& column, int max_step); DataImpl _parsed_data; ColumnPtr _text_column; + DataTypePtr _text_datatype; }; } // namespace doris::vectorized diff --git a/be/src/vec/functions/function_fake.cpp b/be/src/vec/functions/function_fake.cpp index 0353b3a2a7c..c7edcf4df8f 100644 --- a/be/src/vec/functions/function_fake.cpp +++ b/be/src/vec/functions/function_fake.cpp @@ -38,7 +38,7 @@ namespace doris::vectorized { -template <typename ReturnType, bool AlwaysNullable = false> +template <typename ReturnType, bool AlwaysNullable = false, bool VARIADIC = false> struct FunctionFakeBaseImpl { static DataTypePtr get_return_type_impl(const DataTypes& arguments) { if constexpr (AlwaysNullable) { @@ -46,6 +46,16 @@ struct FunctionFakeBaseImpl { } return std::make_shared<ReturnType>(); } + static DataTypes get_variadic_argument_types() { + if constexpr (VARIADIC) { + if constexpr (AlwaysNullable) { + return {make_nullable(std::make_shared<ReturnType>())}; + } + return {std::make_shared<ReturnType>()}; + } else { + return {}; + } + } static std::string get_error_msg() { return "Fake function do not support execute"; } }; @@ -55,6 +65,7 @@ struct FunctionExplode { return make_nullable( check_and_get_data_type<DataTypeArray>(arguments[0].get())->get_nested_type()); } + static DataTypes get_variadic_argument_types() { return {}; } static std::string get_error_msg() { return "Fake function do not support execute"; } }; @@ -67,6 +78,7 @@ struct FunctionExplodeMap { fieldTypes[1] = check_and_get_data_type<DataTypeMap>(arguments[0].get())->get_value_type(); return make_nullable(std::make_shared<vectorized::DataTypeStruct>(fieldTypes)); } + static DataTypes get_variadic_argument_types() { return {}; } static std::string get_error_msg() { return "Fake function do not support execute"; } }; @@ -80,6 +92,7 @@ struct FunctionExplodeJsonObject { fieldTypes[1] = make_nullable(std::make_shared<DataTypeJsonb>()); return make_nullable(std::make_shared<vectorized::DataTypeStruct>(fieldTypes)); } + static DataTypes get_variadic_argument_types() { return {}; } static std::string get_error_msg() { return "Fake function do not support execute"; } }; @@ -87,6 +100,7 @@ struct FunctionEsquery { static DataTypePtr get_return_type_impl(const DataTypes& arguments) { return FunctionFakeBaseImpl<DataTypeUInt8>::get_return_type_impl(arguments); } + static DataTypes get_variadic_argument_types() { return {}; } static std::string get_error_msg() { return "esquery only supported on es table"; } }; @@ -102,11 +116,13 @@ void register_table_function_expand(SimpleFunctionFactory& factory, const std::s factory.register_function<FunctionFake<FunctionImpl>>(name + suffix); }; -template <typename ReturnType> +template <typename ReturnType, bool VARIADIC> void register_table_function_expand_default(SimpleFunctionFactory& factory, const std::string& name, const std::string& suffix) { - factory.register_function<FunctionFake<FunctionFakeBaseImpl<ReturnType>>>(name); - factory.register_function<FunctionFake<FunctionFakeBaseImpl<ReturnType, true>>>(name + suffix); + factory.register_function<FunctionFake<FunctionFakeBaseImpl<ReturnType, false, VARIADIC>>>( + name); + factory.register_function<FunctionFake<FunctionFakeBaseImpl<ReturnType, true, VARIADIC>>>( + name + suffix); }; template <typename FunctionImpl> @@ -114,10 +130,11 @@ void register_table_function_expand_outer(SimpleFunctionFactory& factory, const register_table_function_expand<FunctionImpl>(factory, name, COMBINATOR_SUFFIX_OUTER); }; -template <typename ReturnType> +template <typename ReturnType, bool VARIADIC> void register_table_function_expand_outer_default(SimpleFunctionFactory& factory, const std::string& name) { - register_table_function_expand_default<ReturnType>(factory, name, COMBINATOR_SUFFIX_OUTER); + register_table_function_expand_default<ReturnType, VARIADIC>(factory, name, + COMBINATOR_SUFFIX_OUTER); }; void register_function_fake(SimpleFunctionFactory& factory) { @@ -127,16 +144,19 @@ void register_function_fake(SimpleFunctionFactory& factory) { register_table_function_expand_outer<FunctionExplodeMap>(factory, "explode_map"); register_table_function_expand_outer<FunctionExplodeJsonObject>(factory, "explode_json_object"); - register_table_function_expand_outer_default<DataTypeString>(factory, "explode_split"); - register_table_function_expand_outer_default<DataTypeInt32>(factory, "explode_numbers"); - register_table_function_expand_outer_default<DataTypeInt64>(factory, "explode_json_array_int"); - register_table_function_expand_outer_default<DataTypeString>(factory, - "explode_json_array_string"); - register_table_function_expand_outer_default<DataTypeString>(factory, - "explode_json_array_json"); - register_table_function_expand_outer_default<DataTypeFloat64>(factory, - "explode_json_array_double"); - register_table_function_expand_outer_default<DataTypeInt64>(factory, "explode_bitmap"); + register_table_function_expand_outer_default<DataTypeString, false>(factory, "explode_split"); + register_table_function_expand_outer_default<DataTypeInt32, false>(factory, "explode_numbers"); + register_table_function_expand_outer_default<DataTypeInt64, false>(factory, + "explode_json_array_int"); + register_table_function_expand_outer_default<DataTypeString, false>( + factory, "explode_json_array_string"); + register_table_function_expand_outer_default<DataTypeJsonb, true>(factory, + "explode_json_array_json"); + register_table_function_expand_outer_default<DataTypeString, true>(factory, + "explode_json_array_json"); + register_table_function_expand_outer_default<DataTypeFloat64, false>( + factory, "explode_json_array_double"); + register_table_function_expand_outer_default<DataTypeInt64, false>(factory, "explode_bitmap"); } } // namespace doris::vectorized diff --git a/be/src/vec/functions/function_fake.h b/be/src/vec/functions/function_fake.h index 0dabdfb3c83..dfbfce2127d 100644 --- a/be/src/vec/functions/function_fake.h +++ b/be/src/vec/functions/function_fake.h @@ -35,6 +35,7 @@ class Block; } // namespace doris namespace doris::vectorized { + // FunctionFake is use for some function call expr only work at prepare/open phase, do not support execute(). template <typename Impl> class FunctionFake : public IFunction { @@ -55,6 +56,10 @@ public: bool use_default_implementation_for_nulls() const override { return true; } + DataTypes get_variadic_argument_types_impl() const override { + return Impl::get_variadic_argument_types(); + } + bool use_default_implementation_for_constants() const override { return false; } Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments, diff --git a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayDouble.java b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayDouble.java index e6072931325..c24477c20d1 100644 --- a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayDouble.java +++ b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayDouble.java @@ -23,6 +23,7 @@ import org.apache.doris.nereids.trees.expressions.functions.PropagateNullable; import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression; import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor; import org.apache.doris.nereids.types.DoubleType; +import org.apache.doris.nereids.types.JsonType; import org.apache.doris.nereids.types.VarcharType; import com.google.common.base.Preconditions; @@ -36,6 +37,7 @@ import java.util.List; public class ExplodeJsonArrayDouble extends TableGeneratingFunction implements UnaryExpression, PropagateNullable { public static final List<FunctionSignature> SIGNATURES = ImmutableList.of( + FunctionSignature.ret(DoubleType.INSTANCE).args(JsonType.INSTANCE), FunctionSignature.ret(DoubleType.INSTANCE).args(VarcharType.SYSTEM_DEFAULT) ); diff --git a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayDoubleOuter.java b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayDoubleOuter.java index 1bb8c0383f4..a2e3609c48c 100644 --- a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayDoubleOuter.java +++ b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayDoubleOuter.java @@ -23,6 +23,7 @@ import org.apache.doris.nereids.trees.expressions.functions.AlwaysNullable; import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression; import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor; import org.apache.doris.nereids.types.DoubleType; +import org.apache.doris.nereids.types.JsonType; import org.apache.doris.nereids.types.VarcharType; import com.google.common.base.Preconditions; @@ -36,6 +37,7 @@ import java.util.List; public class ExplodeJsonArrayDoubleOuter extends TableGeneratingFunction implements UnaryExpression, AlwaysNullable { public static final List<FunctionSignature> SIGNATURES = ImmutableList.of( + FunctionSignature.ret(DoubleType.INSTANCE).args(JsonType.INSTANCE), FunctionSignature.ret(DoubleType.INSTANCE).args(VarcharType.SYSTEM_DEFAULT) ); diff --git a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayInt.java b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayInt.java index 17277e1c967..86db7573375 100644 --- a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayInt.java +++ b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayInt.java @@ -23,6 +23,7 @@ import org.apache.doris.nereids.trees.expressions.functions.PropagateNullable; import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression; import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor; import org.apache.doris.nereids.types.BigIntType; +import org.apache.doris.nereids.types.JsonType; import org.apache.doris.nereids.types.VarcharType; import com.google.common.base.Preconditions; @@ -36,6 +37,7 @@ import java.util.List; public class ExplodeJsonArrayInt extends TableGeneratingFunction implements UnaryExpression, PropagateNullable { public static final List<FunctionSignature> SIGNATURES = ImmutableList.of( + FunctionSignature.ret(BigIntType.INSTANCE).args(JsonType.INSTANCE), FunctionSignature.ret(BigIntType.INSTANCE).args(VarcharType.SYSTEM_DEFAULT) ); diff --git a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayIntOuter.java b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayIntOuter.java index 2a8820c717c..fb7360959a4 100644 --- a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayIntOuter.java +++ b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayIntOuter.java @@ -23,6 +23,7 @@ import org.apache.doris.nereids.trees.expressions.functions.AlwaysNullable; import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression; import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor; import org.apache.doris.nereids.types.BigIntType; +import org.apache.doris.nereids.types.JsonType; import org.apache.doris.nereids.types.VarcharType; import com.google.common.base.Preconditions; @@ -36,6 +37,7 @@ import java.util.List; public class ExplodeJsonArrayIntOuter extends TableGeneratingFunction implements UnaryExpression, AlwaysNullable { public static final List<FunctionSignature> SIGNATURES = ImmutableList.of( + FunctionSignature.ret(BigIntType.INSTANCE).args(JsonType.INSTANCE), FunctionSignature.ret(BigIntType.INSTANCE).args(VarcharType.SYSTEM_DEFAULT) ); diff --git a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayJson.java b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayJson.java index a07e0e5d8fa..6209f23a7dd 100644 --- a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayJson.java +++ b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayJson.java @@ -22,6 +22,7 @@ import org.apache.doris.nereids.trees.expressions.Expression; import org.apache.doris.nereids.trees.expressions.functions.PropagateNullable; import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression; import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor; +import org.apache.doris.nereids.types.JsonType; import org.apache.doris.nereids.types.VarcharType; import com.google.common.base.Preconditions; @@ -35,6 +36,7 @@ import java.util.List; */ public class ExplodeJsonArrayJson extends TableGeneratingFunction implements UnaryExpression, PropagateNullable { public static final List<FunctionSignature> SIGNATURES = ImmutableList.of( + FunctionSignature.ret(JsonType.INSTANCE).args(JsonType.INSTANCE), FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).args(VarcharType.SYSTEM_DEFAULT) ); diff --git a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayJsonOuter.java b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayJsonOuter.java index bb4a34905a4..ab358855196 100644 --- a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayJsonOuter.java +++ b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayJsonOuter.java @@ -22,6 +22,7 @@ import org.apache.doris.nereids.trees.expressions.Expression; import org.apache.doris.nereids.trees.expressions.functions.PropagateNullable; import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression; import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor; +import org.apache.doris.nereids.types.JsonType; import org.apache.doris.nereids.types.VarcharType; import com.google.common.base.Preconditions; @@ -35,6 +36,7 @@ import java.util.List; */ public class ExplodeJsonArrayJsonOuter extends TableGeneratingFunction implements UnaryExpression, PropagateNullable { public static final List<FunctionSignature> SIGNATURES = ImmutableList.of( + FunctionSignature.ret(JsonType.INSTANCE).args(JsonType.INSTANCE), FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).args(VarcharType.SYSTEM_DEFAULT) ); diff --git a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayString.java b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayString.java index 653cb36ca21..04717cd5c09 100644 --- a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayString.java +++ b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayString.java @@ -22,6 +22,7 @@ import org.apache.doris.nereids.trees.expressions.Expression; import org.apache.doris.nereids.trees.expressions.functions.PropagateNullable; import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression; import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor; +import org.apache.doris.nereids.types.JsonType; import org.apache.doris.nereids.types.VarcharType; import com.google.common.base.Preconditions; @@ -35,6 +36,7 @@ import java.util.List; public class ExplodeJsonArrayString extends TableGeneratingFunction implements UnaryExpression, PropagateNullable { public static final List<FunctionSignature> SIGNATURES = ImmutableList.of( + FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).args(JsonType.INSTANCE), FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).args(VarcharType.SYSTEM_DEFAULT) ); diff --git a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayStringOuter.java b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayStringOuter.java index dfb21ab826f..03507aa9799 100644 --- a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayStringOuter.java +++ b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/generator/ExplodeJsonArrayStringOuter.java @@ -22,6 +22,7 @@ import org.apache.doris.nereids.trees.expressions.Expression; import org.apache.doris.nereids.trees.expressions.functions.AlwaysNullable; import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression; import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor; +import org.apache.doris.nereids.types.JsonType; import org.apache.doris.nereids.types.VarcharType; import com.google.common.base.Preconditions; @@ -35,6 +36,7 @@ import java.util.List; public class ExplodeJsonArrayStringOuter extends TableGeneratingFunction implements UnaryExpression, AlwaysNullable { public static final List<FunctionSignature> SIGNATURES = ImmutableList.of( + FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).args(JsonType.INSTANCE), FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).args(VarcharType.SYSTEM_DEFAULT) ); diff --git a/regression-test/data/nereids_function_p0/gen_function/gen.out b/regression-test/data/nereids_function_p0/gen_function/gen.out index 17f86d875e0..286a05ee85b 100644 --- a/regression-test/data/nereids_function_p0/gen_function/gen.out +++ b/regression-test/data/nereids_function_p0/gen_function/gen.out @@ -757,6 +757,47 @@ 11 {"id":2,"name":"Mary"} 11 {"id":3,"name":"Bob"} +-- !sql_explode_json_array_json_Json -- +\N {"id":1,"name":"John"} +\N {"id":2,"name":"Mary"} +\N {"id":3,"name":"Bob"} +0 {"id":1,"name":"John"} +0 {"id":2,"name":"Mary"} +0 {"id":3,"name":"Bob"} +1 {"id":1,"name":"John"} +1 {"id":2,"name":"Mary"} +1 {"id":3,"name":"Bob"} +2 {"id":1,"name":"John"} +2 {"id":2,"name":"Mary"} +2 {"id":3,"name":"Bob"} +3 {"id":1,"name":"John"} +3 {"id":2,"name":"Mary"} +3 {"id":3,"name":"Bob"} +4 {"id":1,"name":"John"} +4 {"id":2,"name":"Mary"} +4 {"id":3,"name":"Bob"} +5 {"id":1,"name":"John"} +5 {"id":2,"name":"Mary"} +5 {"id":3,"name":"Bob"} +6 {"id":1,"name":"John"} +6 {"id":2,"name":"Mary"} +6 {"id":3,"name":"Bob"} +7 {"id":1,"name":"John"} +7 {"id":2,"name":"Mary"} +7 {"id":3,"name":"Bob"} +8 {"id":1,"name":"John"} +8 {"id":2,"name":"Mary"} +8 {"id":3,"name":"Bob"} +9 {"id":1,"name":"John"} +9 {"id":2,"name":"Mary"} +9 {"id":3,"name":"Bob"} +10 {"id":1,"name":"John"} +10 {"id":2,"name":"Mary"} +10 {"id":3,"name":"Bob"} +11 {"id":1,"name":"John"} +11 {"id":2,"name":"Mary"} +11 {"id":3,"name":"Bob"} + -- !sql_explode_Double -- 0 0.1 1 0.2 diff --git a/regression-test/data/query_p0/sql_functions/table_function/explode_json_array.out b/regression-test/data/query_p0/sql_functions/table_function/explode_json_array.out index ccc012e1121..f75b56b3305 100644 --- a/regression-test/data/query_p0/sql_functions/table_function/explode_json_array.out +++ b/regression-test/data/query_p0/sql_functions/table_function/explode_json_array.out @@ -79,7 +79,21 @@ \N 80 3 \N 80 b --- !outer_join_explode_json_array11 -- +-- !outer_join_explode_json_array111 -- +\N \N {"id":1,"name":"John"} +\N \N {"id":2,"name":"Mary"} +\N \N {"id":3,"name":"Bob"} +\N 30 {"id":1,"name":"John"} +\N 30 {"id":2,"name":"Mary"} +\N 30 {"id":3,"name":"Bob"} +\N 50 {"id":1,"name":"John"} +\N 50 {"id":2,"name":"Mary"} +\N 50 {"id":3,"name":"Bob"} +\N 80 {"id":1,"name":"John"} +\N 80 {"id":2,"name":"Mary"} +\N 80 {"id":3,"name":"Bob"} + +-- !outer_join_explode_json_array112 -- \N \N {"id":1,"name":"John"} \N \N {"id":2,"name":"Mary"} \N \N {"id":3,"name":"Bob"} diff --git a/regression-test/suites/nereids_function_p0/gen_function/gen.groovy b/regression-test/suites/nereids_function_p0/gen_function/gen.groovy index 547ee40a220..7f30c9a2b6a 100644 --- a/regression-test/suites/nereids_function_p0/gen_function/gen.groovy +++ b/regression-test/suites/nereids_function_p0/gen_function/gen.groovy @@ -62,6 +62,9 @@ suite("nereids_gen_fn") { qt_sql_explode_json_array_json_Varchar ''' select id, e from fn_test lateral view explode_json_array_json('[{"id":1,"name":"John"},{"id":2,"name":"Mary"},{"id":3,"name":"Bob"}]') lv as e order by id, e''' + qt_sql_explode_json_array_json_Json ''' + select id, e from fn_test lateral view explode_json_array_json(cast('[{"id":1,"name":"John"},{"id":2,"name":"Mary"},{"id":3,"name":"Bob"}]' as json)) lv as e order by id, cast(e as string); ''' + // explode order_qt_sql_explode_Double "select id, e from fn_test lateral view explode(kadbl) lv as e order by id, e" order_qt_sql_explode_Double_notnull "select id, e from fn_test_not_nullable lateral view explode(kadbl) lv as e order by id, e" diff --git a/regression-test/suites/query_p0/sql_functions/table_function/explode_json_array.groovy b/regression-test/suites/query_p0/sql_functions/table_function/explode_json_array.groovy index e6ed1b62a24..edc1bc7fa1a 100644 --- a/regression-test/suites/query_p0/sql_functions/table_function/explode_json_array.groovy +++ b/regression-test/suites/query_p0/sql_functions/table_function/explode_json_array.groovy @@ -60,10 +60,14 @@ suite("explode_json_array") { qt_outer_join_explode_json_array11 """SELECT id, age, e1 FROM (SELECT id, age, e1 FROM (SELECT b.id, a.age FROM person a LEFT JOIN person b ON a.id=b.age)T LATERAL VIEW EXPLODE_JSON_ARRAY_STRING('[1, "b", 3]') TMP AS e1) AS T ORDER BY age, e1""" - qt_outer_join_explode_json_array11 """SELECT id, age, e1 FROM (SELECT id, age, e1 FROM (SELECT b.id, a.age FROM + qt_outer_join_explode_json_array111 """SELECT id, age, e1 FROM (SELECT id, age, e1 FROM (SELECT b.id, a.age FROM person a LEFT JOIN person b ON a.id=b.age)T LATERAL VIEW EXPLODE_JSON_ARRAY_JSON('[{"id":1,"name":"John"},{"id":2,"name":"Mary"},{"id":3,"name":"Bob"}]') TMP AS e1) AS T ORDER BY age, e1""" + qt_outer_join_explode_json_array112 """SELECT id, age, e1 FROM (SELECT id, age, e1 FROM (SELECT b.id, a.age FROM + person a LEFT JOIN person b ON a.id=b.age)T LATERAL VIEW EXPLODE_JSON_ARRAY_JSON(cast('[{"id":1,"name":"John"},{"id":2,"name":"Mary"},{"id":3,"name":"Bob"}]' as Json)) + TMP AS e1) AS T ORDER BY age, cast(e1 as string)""" + qt_explode_json_array12 """ SELECT c_age, COUNT(1) FROM person LATERAL VIEW EXPLODE_JSON_ARRAY_INT('[9223372036854775807,9223372036854775808]') t1 as c_age GROUP BY c_age ORDER BY c_age """ --------------------------------------------------------------------- To unsubscribe, e-mail: commits-unsubscr...@doris.apache.org For additional commands, e-mail: commits-h...@doris.apache.org