This is an automated email from the ASF dual-hosted git repository.
yiguolei 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 90e22197ff0 [fix](json-functions)fix json-replace/insert/set/array
behavior with complex type #50308 (#50309)
90e22197ff0 is described below
commit 90e22197ff0e78522d4278945b10f2f245ad9b2a
Author: amory <[email protected]>
AuthorDate: Thu Apr 24 19:04:25 2025 +0800
[fix](json-functions)fix json-replace/insert/set/array behavior with
complex type #50308 (#50309)
### What problem does this PR solve?
backport: https://github.com/apache/doris/pull/50308
Issue Number: close #xxx
Related PR: #xxx
Problem Summary:
### Release note
None
### Check List (For Author)
- Test <!-- At least one of them must be included. -->
- [ ] Regression test
- [ ] Unit Test
- [ ] Manual test (add detailed scripts or steps below)
- [ ] No need to test or manual test. Explain why:
- [ ] This is a refactor/code format and no logic has been changed.
- [ ] Previous test can cover this change.
- [ ] No code files have been changed.
- [ ] Other reason <!-- Add your reason? -->
- Behavior changed:
- [ ] No.
- [ ] Yes. <!-- Explain the behavior change -->
- Does this need documentation?
- [ ] No.
- [ ] Yes. <!-- Add document PR link here. eg:
https://github.com/apache/doris-website/pull/1214 -->
### Check List (For Reviewer who merge this PR)
- [ ] Confirm the release note
- [ ] Confirm test cases
- [ ] Confirm document
- [ ] Add branch pick label <!-- Add branch pick label that this PR
should merge into -->
---
.../vec/data_types/serde/data_type_jsonb_serde.cpp | 4 +-
.../vec/data_types/serde/data_type_jsonb_serde.h | 3 ++
be/src/vec/functions/function_json.cpp | 19 +++++--
.../apache/doris/analysis/FunctionCallExpr.java | 2 +
.../expressions/functions/scalar/JsonArray.java | 33 ++++++------
.../expressions/functions/scalar/JsonInsert.java | 33 +++++++-----
.../expressions/functions/scalar/JsonObject.java | 36 +++++++------
.../expressions/functions/scalar/JsonReplace.java | 33 +++++++-----
.../expressions/functions/scalar/JsonSet.java | 33 +++++++-----
.../query_p0/cast/test_complextype_to_json.out | Bin 2450 -> 2124 bytes
.../json_function/test_query_json_array.out | Bin 485 -> 1395 bytes
.../json_function/test_query_json_insert.out | Bin 423 -> 1785 bytes
.../json_function/test_query_json_object.out | Bin 524 -> 1959 bytes
.../json_function/test_query_json_replace.out | Bin 543 -> 1752 bytes
.../json_function/test_query_json_set.out | Bin 385 -> 1594 bytes
.../json_function/test_query_json_array.groovy | 51 +++++++++++++++++++
.../json_function/test_query_json_insert.groovy | 55 ++++++++++++++++++++
.../json_function/test_query_json_object.groovy | 56 +++++++++++++++++++++
.../json_function/test_query_json_replace.groovy | 55 ++++++++++++++++++++
.../json_function/test_query_json_set.groovy | 55 ++++++++++++++++++++
20 files changed, 396 insertions(+), 72 deletions(-)
diff --git a/be/src/vec/data_types/serde/data_type_jsonb_serde.cpp
b/be/src/vec/data_types/serde/data_type_jsonb_serde.cpp
index 079af137310..08514a6eea7 100644
--- a/be/src/vec/data_types/serde/data_type_jsonb_serde.cpp
+++ b/be/src/vec/data_types/serde/data_type_jsonb_serde.cpp
@@ -139,8 +139,8 @@ Status DataTypeJsonbSerDe::write_column_to_orc(const
std::string& timezone, cons
return Status::NotSupported("write_column_to_orc with type [{}]",
column.get_name());
}
-static void convert_jsonb_to_rapidjson(const JsonbValue& val,
rapidjson::Value& target,
- rapidjson::Document::AllocatorType&
allocator) {
+void convert_jsonb_to_rapidjson(const JsonbValue& val, rapidjson::Value&
target,
+ rapidjson::Document::AllocatorType& allocator)
{
// convert type of jsonb to rapidjson::Value
switch (val.type()) {
case JsonbType::T_True:
diff --git a/be/src/vec/data_types/serde/data_type_jsonb_serde.h
b/be/src/vec/data_types/serde/data_type_jsonb_serde.h
index e868ad9a6df..f1c5969f4c0 100644
--- a/be/src/vec/data_types/serde/data_type_jsonb_serde.h
+++ b/be/src/vec/data_types/serde/data_type_jsonb_serde.h
@@ -76,5 +76,8 @@ private:
Status _write_column_to_mysql(const IColumn& column,
MysqlRowBuffer<is_binary_format>& result,
int row_idx, bool col_const, const
FormatOptions& options) const;
};
+
+void convert_jsonb_to_rapidjson(const JsonbValue& val, rapidjson::Value&
target,
+ rapidjson::Document::AllocatorType& allocator);
} // namespace vectorized
} // namespace doris
diff --git a/be/src/vec/functions/function_json.cpp
b/be/src/vec/functions/function_json.cpp
index ca2a605f48d..44830340822 100644
--- a/be/src/vec/functions/function_json.cpp
+++ b/be/src/vec/functions/function_json.cpp
@@ -65,6 +65,7 @@
#include "vec/data_types/data_type_nullable.h"
#include "vec/data_types/data_type_number.h"
#include "vec/data_types/data_type_string.h"
+#include "vec/data_types/serde/data_type_jsonb_serde.h"
#include "vec/functions/function.h"
#include "vec/functions/function_string.h"
#include "vec/functions/function_totype.h"
@@ -608,6 +609,18 @@ struct JsonParser<'5'> {
}
};
+template <>
+struct JsonParser<'7'> {
+ // json string
+ static void update_value(StringParser::ParseResult& result,
rapidjson::Value& value,
+ StringRef data,
rapidjson::Document::AllocatorType& allocator) {
+ rapidjson::Document document;
+ JsonbValue* json_val = JsonbDocument::createValue(data.data,
data.size);
+ doris::vectorized::convert_jsonb_to_rapidjson(*json_val, document,
allocator);
+ value.CopyFrom(document, allocator);
+ }
+};
+
template <int flag, typename Impl>
struct ExecuteReducer {
template <typename... TArgs>
@@ -629,7 +642,7 @@ struct FunctionJsonArrayImpl {
rapidjson::Document::AllocatorType& allocator,
const std::vector<const ColumnUInt8*>& nullmaps)
{
for (int i = 0; i < data_columns.size() - 1; i++) {
- constexpr_int_match<'0', '6', Reducer>::run(type_flags[i],
objects, allocator,
+ constexpr_int_match<'0', '7', Reducer>::run(type_flags[i],
objects, allocator,
data_columns[i],
nullmaps[i]);
}
}
@@ -669,7 +682,7 @@ struct FunctionJsonObjectImpl {
}
for (int i = 0; i + 1 < data_columns.size() - 1; i += 2) {
- constexpr_int_match<'0', '6', Reducer>::run(type_flags[i + 1],
objects, allocator,
+ constexpr_int_match<'0', '7', Reducer>::run(type_flags[i + 1],
objects, allocator,
data_columns[i],
data_columns[i + 1],
nullmaps[i + 1]);
}
@@ -1432,7 +1445,7 @@ public:
const std::vector<const ColumnUInt8*>& nullmaps,
std::vector<bool>& column_is_consts) {
for (auto col = 1; col + 1 < data_columns.size() - 1; col += 2) {
- constexpr_int_match<'0', '6', Reducer>::run(
+ constexpr_int_match<'0', '7', Reducer>::run(
type_flags[col + 1], objects, json_paths[col / 2],
data_columns[col + 1],
nullmaps[col + 1], column_is_consts[col + 1]);
}
diff --git
a/fe/fe-core/src/main/java/org/apache/doris/analysis/FunctionCallExpr.java
b/fe/fe-core/src/main/java/org/apache/doris/analysis/FunctionCallExpr.java
index 7b2189f7a73..6ef80c193ba 100644
--- a/fe/fe-core/src/main/java/org/apache/doris/analysis/FunctionCallExpr.java
+++ b/fe/fe-core/src/main/java/org/apache/doris/analysis/FunctionCallExpr.java
@@ -488,6 +488,8 @@ public class FunctionCallExpr extends Expr {
return 3;
} else if (type.isTime()) {
return 4;
+ } else if (type.isComplexType() || type.isJsonbType()) {
+ return 7;
} else {
return 6;
}
diff --git
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonArray.java
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonArray.java
index 51d8d4f4e6c..581b21bc589 100644
---
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonArray.java
+++
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonArray.java
@@ -20,24 +20,20 @@ package
org.apache.doris.nereids.trees.expressions.functions.scalar;
import org.apache.doris.catalog.FunctionSignature;
import org.apache.doris.nereids.trees.expressions.Expression;
import org.apache.doris.nereids.trees.expressions.functions.AlwaysNotNullable;
-import
org.apache.doris.nereids.trees.expressions.functions.ExplicitlyCastableSignature;
+import org.apache.doris.nereids.trees.expressions.functions.CustomSignature;
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
+import org.apache.doris.nereids.types.DataType;
+import org.apache.doris.nereids.types.JsonType;
import org.apache.doris.nereids.types.VarcharType;
import org.apache.doris.nereids.util.ExpressionUtils;
-import com.google.common.collect.ImmutableList;
-
+import java.util.ArrayList;
import java.util.List;
/**
* ScalarFunction 'json_array'. This class is generated by GenerateFunction.
*/
-public class JsonArray extends ScalarFunction
- implements ExplicitlyCastableSignature, AlwaysNotNullable {
-
- public static final List<FunctionSignature> SIGNATURES = ImmutableList.of(
-
FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).varArgs(VarcharType.SYSTEM_DEFAULT)
- );
+public class JsonArray extends ScalarFunction implements CustomSignature,
AlwaysNotNullable {
/**
* constructor with 0 or more arguments.
@@ -46,6 +42,20 @@ public class JsonArray extends ScalarFunction
super("json_array", ExpressionUtils.mergeArguments(varArgs));
}
+ @Override
+ public FunctionSignature customSignature() {
+ List<DataType> arguments = new ArrayList<>();
+ for (int i = 0; i < arity(); i++) {
+ if (getArgumentType(i).isComplexType() ||
getArgumentType(i).isJsonType()) {
+ // keep origin type for BE Serialization
+ arguments.add(JsonType.INSTANCE);
+ } else {
+ arguments.add(VarcharType.SYSTEM_DEFAULT);
+ }
+ }
+ return FunctionSignature.of(VarcharType.SYSTEM_DEFAULT, arguments);
+ }
+
/**
* withChildren.
*/
@@ -54,11 +64,6 @@ public class JsonArray extends ScalarFunction
return new JsonArray(children.toArray(new Expression[0]));
}
- @Override
- public List<FunctionSignature> getSignatures() {
- return SIGNATURES;
- }
-
@Override
public <R, C> R accept(ExpressionVisitor<R, C> visitor, C context) {
return visitor.visitJsonArray(this, context);
diff --git
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonInsert.java
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonInsert.java
index 8f9c9900aec..397067509c6 100644
---
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonInsert.java
+++
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonInsert.java
@@ -19,26 +19,23 @@ package
org.apache.doris.nereids.trees.expressions.functions.scalar;
import org.apache.doris.catalog.FunctionSignature;
import org.apache.doris.nereids.trees.expressions.Expression;
-import
org.apache.doris.nereids.trees.expressions.functions.ExplicitlyCastableSignature;
+import org.apache.doris.nereids.trees.expressions.functions.CustomSignature;
import org.apache.doris.nereids.trees.expressions.functions.PropagateNullable;
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
+import org.apache.doris.nereids.types.DataType;
+import org.apache.doris.nereids.types.JsonType;
import org.apache.doris.nereids.types.VarcharType;
import org.apache.doris.nereids.util.ExpressionUtils;
import com.google.common.base.Preconditions;
-import com.google.common.collect.ImmutableList;
+import java.util.ArrayList;
import java.util.List;
/**
* ScalarFunction 'json_insert'. This class is generated by GenerateFunction.
*/
-public class JsonInsert extends ScalarFunction
- implements ExplicitlyCastableSignature, PropagateNullable {
-
- public static final List<FunctionSignature> SIGNATURES =
- ImmutableList.of(FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT)
- .varArgs(VarcharType.SYSTEM_DEFAULT, VarcharType.SYSTEM_DEFAULT,
VarcharType.SYSTEM_DEFAULT));
+public class JsonInsert extends ScalarFunction implements CustomSignature,
PropagateNullable {
/**
* constructor with 3 or more arguments.
@@ -47,6 +44,21 @@ public class JsonInsert extends ScalarFunction
super("json_insert", ExpressionUtils.mergeArguments(arg0, arg1, arg2,
varArgs));
}
+ @Override
+ public FunctionSignature customSignature() {
+ List<DataType> arguments = new ArrayList<>();
+ arguments.add(VarcharType.SYSTEM_DEFAULT); // json_str
+ for (int i = 1; i < arity(); i++) {
+ if ((i & 1) == 0 && (getArgumentType(i).isComplexType() ||
getArgumentType(i).isJsonType())) {
+ // keep origin type for BE Serialization
+ arguments.add(JsonType.INSTANCE);
+ } else {
+ arguments.add(VarcharType.SYSTEM_DEFAULT);
+ }
+ }
+ return FunctionSignature.of(VarcharType.SYSTEM_DEFAULT, arguments);
+ }
+
/**
* withChildren.
*/
@@ -57,11 +69,6 @@ public class JsonInsert extends ScalarFunction
children.subList(3, children.size()).toArray(new Expression[0]));
}
- @Override
- public List<FunctionSignature> getSignatures() {
- return SIGNATURES;
- }
-
@Override
public <R, C> R accept(ExpressionVisitor<R, C> visitor, C context) {
return visitor.visitJsonInsert(this, context);
diff --git
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonObject.java
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonObject.java
index 6d3d1536eb8..9c9fe55ace8 100644
---
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonObject.java
+++
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonObject.java
@@ -21,24 +21,23 @@ import org.apache.doris.catalog.FunctionSignature;
import org.apache.doris.nereids.exceptions.AnalysisException;
import org.apache.doris.nereids.trees.expressions.Expression;
import org.apache.doris.nereids.trees.expressions.functions.AlwaysNotNullable;
-import
org.apache.doris.nereids.trees.expressions.functions.ExplicitlyCastableSignature;
+import org.apache.doris.nereids.trees.expressions.functions.CustomSignature;
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
+import org.apache.doris.nereids.types.DataType;
+import org.apache.doris.nereids.types.JsonType;
import org.apache.doris.nereids.types.VarcharType;
import org.apache.doris.nereids.util.ExpressionUtils;
-import com.google.common.collect.ImmutableList;
-
+import java.util.ArrayList;
import java.util.List;
/**
* ScalarFunction 'json_object'. This class is generated by GenerateFunction.
+ * Builds a JSON object out of a variadic argument list.
+ * By convention, the argument list consists of alternating keys and values.
+ * Key arguments are coerced to text; value arguments are converted as per
to_json or to_jsonb.
*/
-public class JsonObject extends ScalarFunction
- implements ExplicitlyCastableSignature, AlwaysNotNullable {
-
- public static final List<FunctionSignature> SIGNATURES = ImmutableList.of(
-
FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).varArgs(VarcharType.SYSTEM_DEFAULT)
- );
+public class JsonObject extends ScalarFunction implements CustomSignature,
AlwaysNotNullable {
/**
* constructor with 0 or more arguments.
@@ -47,6 +46,20 @@ public class JsonObject extends ScalarFunction
super("json_object", ExpressionUtils.mergeArguments(varArgs));
}
+ @Override
+ public FunctionSignature customSignature() {
+ List<DataType> arguments = new ArrayList<>();
+ for (int i = 0; i < arity(); i++) {
+ if (getArgumentType(i).isComplexType() ||
getArgumentType(i).isJsonType()) {
+ // keep origin type for BE Serialization
+ arguments.add(JsonType.INSTANCE);
+ } else {
+ arguments.add(VarcharType.SYSTEM_DEFAULT);
+ }
+ }
+ return FunctionSignature.of(VarcharType.SYSTEM_DEFAULT, arguments);
+ }
+
@Override
public void checkLegalityBeforeTypeCoercion() {
if ((arity() & 1) == 1) {
@@ -67,11 +80,6 @@ public class JsonObject extends ScalarFunction
return new JsonObject(children.toArray(new Expression[0]));
}
- @Override
- public List<FunctionSignature> getSignatures() {
- return SIGNATURES;
- }
-
@Override
public <R, C> R accept(ExpressionVisitor<R, C> visitor, C context) {
return visitor.visitJsonObject(this, context);
diff --git
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonReplace.java
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonReplace.java
index c5ced84ac8e..69e424df1fd 100644
---
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonReplace.java
+++
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonReplace.java
@@ -19,26 +19,23 @@ package
org.apache.doris.nereids.trees.expressions.functions.scalar;
import org.apache.doris.catalog.FunctionSignature;
import org.apache.doris.nereids.trees.expressions.Expression;
-import
org.apache.doris.nereids.trees.expressions.functions.ExplicitlyCastableSignature;
+import org.apache.doris.nereids.trees.expressions.functions.CustomSignature;
import org.apache.doris.nereids.trees.expressions.functions.PropagateNullable;
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
+import org.apache.doris.nereids.types.DataType;
+import org.apache.doris.nereids.types.JsonType;
import org.apache.doris.nereids.types.VarcharType;
import org.apache.doris.nereids.util.ExpressionUtils;
import com.google.common.base.Preconditions;
-import com.google.common.collect.ImmutableList;
+import java.util.ArrayList;
import java.util.List;
/**
* ScalarFunction 'json_replace'. This class is generated by GenerateFunction.
*/
-public class JsonReplace extends ScalarFunction
- implements ExplicitlyCastableSignature, PropagateNullable {
-
- public static final List<FunctionSignature> SIGNATURES =
- ImmutableList.of(FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT)
- .varArgs(VarcharType.SYSTEM_DEFAULT, VarcharType.SYSTEM_DEFAULT,
VarcharType.SYSTEM_DEFAULT));
+public class JsonReplace extends ScalarFunction implements CustomSignature,
PropagateNullable {
/**
* constructor with 3 or more arguments.
@@ -47,6 +44,21 @@ public class JsonReplace extends ScalarFunction
super("json_replace", ExpressionUtils.mergeArguments(arg0, arg1, arg2,
varArgs));
}
+ @Override
+ public FunctionSignature customSignature() {
+ List<DataType> arguments = new ArrayList<>();
+ arguments.add(VarcharType.SYSTEM_DEFAULT); // json_str
+ for (int i = 1; i < arity(); i++) {
+ if ((i & 1) == 0 && (getArgumentType(i).isComplexType() ||
getArgumentType(i).isJsonType())) {
+ // keep origin type for BE Serialization
+ arguments.add(JsonType.INSTANCE);
+ } else {
+ arguments.add(VarcharType.SYSTEM_DEFAULT);
+ }
+ }
+ return FunctionSignature.of(VarcharType.SYSTEM_DEFAULT, arguments);
+ }
+
/**
* withChildren.
*/
@@ -57,11 +69,6 @@ public class JsonReplace extends ScalarFunction
children.subList(3, children.size()).toArray(new Expression[0]));
}
- @Override
- public List<FunctionSignature> getSignatures() {
- return SIGNATURES;
- }
-
@Override
public <R, C> R accept(ExpressionVisitor<R, C> visitor, C context) {
return visitor.visitJsonReplace(this, context);
diff --git
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonSet.java
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonSet.java
index 1076e7ff4ec..f3b1345f823 100644
---
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonSet.java
+++
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/JsonSet.java
@@ -19,26 +19,23 @@ package
org.apache.doris.nereids.trees.expressions.functions.scalar;
import org.apache.doris.catalog.FunctionSignature;
import org.apache.doris.nereids.trees.expressions.Expression;
-import
org.apache.doris.nereids.trees.expressions.functions.ExplicitlyCastableSignature;
+import org.apache.doris.nereids.trees.expressions.functions.CustomSignature;
import org.apache.doris.nereids.trees.expressions.functions.PropagateNullable;
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
+import org.apache.doris.nereids.types.DataType;
+import org.apache.doris.nereids.types.JsonType;
import org.apache.doris.nereids.types.VarcharType;
import org.apache.doris.nereids.util.ExpressionUtils;
import com.google.common.base.Preconditions;
-import com.google.common.collect.ImmutableList;
+import java.util.ArrayList;
import java.util.List;
/**
* ScalarFunction 'json_set'. This class is generated by GenerateFunction.
*/
-public class JsonSet extends ScalarFunction
- implements ExplicitlyCastableSignature, PropagateNullable {
-
- public static final List<FunctionSignature> SIGNATURES =
- ImmutableList.of(FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT)
- .varArgs(VarcharType.SYSTEM_DEFAULT, VarcharType.SYSTEM_DEFAULT,
VarcharType.SYSTEM_DEFAULT));
+public class JsonSet extends ScalarFunction implements CustomSignature,
PropagateNullable {
/**
* constructor with 3 or more arguments.
@@ -47,6 +44,21 @@ public class JsonSet extends ScalarFunction
super("json_set", ExpressionUtils.mergeArguments(arg0, arg1, arg2,
varArgs));
}
+ @Override
+ public FunctionSignature customSignature() {
+ List<DataType> arguments = new ArrayList<>();
+ arguments.add(VarcharType.SYSTEM_DEFAULT); // json_str
+ for (int i = 1; i < arity(); i++) {
+ if ((i & 1) == 0 && (getArgumentType(i).isComplexType() ||
getArgumentType(i).isJsonType())) {
+ // keep origin type for BE Serialization
+ arguments.add(JsonType.INSTANCE);
+ } else {
+ arguments.add(VarcharType.SYSTEM_DEFAULT);
+ }
+ }
+ return FunctionSignature.of(VarcharType.SYSTEM_DEFAULT, arguments);
+ }
+
/**
* withChildren.
*/
@@ -57,11 +69,6 @@ public class JsonSet extends ScalarFunction
children.subList(3, children.size()).toArray(new Expression[0]));
}
- @Override
- public List<FunctionSignature> getSignatures() {
- return SIGNATURES;
- }
-
@Override
public <R, C> R accept(ExpressionVisitor<R, C> visitor, C context) {
return visitor.visitJsonSet(this, context);
diff --git a/regression-test/data/query_p0/cast/test_complextype_to_json.out
b/regression-test/data/query_p0/cast/test_complextype_to_json.out
index 7412966f767..c209c387923 100644
Binary files a/regression-test/data/query_p0/cast/test_complextype_to_json.out
and b/regression-test/data/query_p0/cast/test_complextype_to_json.out differ
diff --git
a/regression-test/data/query_p0/sql_functions/json_function/test_query_json_array.out
b/regression-test/data/query_p0/sql_functions/json_function/test_query_json_array.out
index 394d5580ee8..5e170954a96 100644
Binary files
a/regression-test/data/query_p0/sql_functions/json_function/test_query_json_array.out
and
b/regression-test/data/query_p0/sql_functions/json_function/test_query_json_array.out
differ
diff --git
a/regression-test/data/query_p0/sql_functions/json_function/test_query_json_insert.out
b/regression-test/data/query_p0/sql_functions/json_function/test_query_json_insert.out
index 9aa3df9655c..63570a66228 100644
Binary files
a/regression-test/data/query_p0/sql_functions/json_function/test_query_json_insert.out
and
b/regression-test/data/query_p0/sql_functions/json_function/test_query_json_insert.out
differ
diff --git
a/regression-test/data/query_p0/sql_functions/json_function/test_query_json_object.out
b/regression-test/data/query_p0/sql_functions/json_function/test_query_json_object.out
index 13d30f6e75e..f4f51b3d69b 100644
Binary files
a/regression-test/data/query_p0/sql_functions/json_function/test_query_json_object.out
and
b/regression-test/data/query_p0/sql_functions/json_function/test_query_json_object.out
differ
diff --git
a/regression-test/data/query_p0/sql_functions/json_function/test_query_json_replace.out
b/regression-test/data/query_p0/sql_functions/json_function/test_query_json_replace.out
index 3ba95483878..d26983242e3 100644
Binary files
a/regression-test/data/query_p0/sql_functions/json_function/test_query_json_replace.out
and
b/regression-test/data/query_p0/sql_functions/json_function/test_query_json_replace.out
differ
diff --git
a/regression-test/data/query_p0/sql_functions/json_function/test_query_json_set.out
b/regression-test/data/query_p0/sql_functions/json_function/test_query_json_set.out
index b289ec01b1c..0742d28e1f3 100644
Binary files
a/regression-test/data/query_p0/sql_functions/json_function/test_query_json_set.out
and
b/regression-test/data/query_p0/sql_functions/json_function/test_query_json_set.out
differ
diff --git
a/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_array.groovy
b/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_array.groovy
index 4005f75509a..e33df09f1c7 100644
---
a/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_array.groovy
+++
b/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_array.groovy
@@ -42,4 +42,55 @@ suite("test_query_json_array", "query") {
sql "insert into ${tableName} values(5,1,true,'test','2022-01-01
11:11:11');"
qt_sql2 """select json_array('k0',k0,'k1',k1,'k2',k2,'k3',k3,'k4',k4,'k5',
null,'k6','k6') from ${tableName} order by k0"""
sql "DROP TABLE ${tableName};"
+
+ // test json_array with complex type
+ // array
+ qt_sql_array """ SELECT json_array(array('"aaa"','"bbb"')); """
+ qt_sql_array """ SELECT json_array(array('aaa','bbb')); """
+ qt_sql_array """ SELECT json_array(array(1,2)); """
+ qt_sql_array """ SELECT json_array(array(1.1,2.2)); """
+ qt_sql_array """ SELECT json_array(array(1.1,2)); """
+ qt_sql_array """ SELECT json_array(array(cast(1 as decimal), cast(1.2 as
decimal))); """
+ // map
+ qt_sql_map """ SELECT json_array(map('a', 'b', 'c', 'd')); """
+ qt_sql_map """ SELECT json_array(map('a', 1, 'c', 2)); """
+ qt_sql_map """ SELECT json_array(map('a', 1.1, 'c', 2.2)); """
+ qt_sql_map """ SELECT json_array(map('a', 1.1, 'c', 2)); """
+ qt_sql_map """ SELECT json_array(map('a', cast(1 as decimal), 'c',
cast(1.2 as decimal))); """
+ // struct
+ qt_sql_struct """ SELECT json_array(named_struct('name', 'a', 'age', 1));
"""
+ qt_sql_struct """ SELECT json_array(named_struct('name', 'a', 'age',
1.1)); """
+ qt_sql_struct """ SELECT json_array(named_struct('name', 'a', 'age',
cast(1 as decimal))); """
+ // json
+ qt_sql_json """ SELECT json_array(cast('{\"a\":\"b\"}' as JSON)); """
+ qt_sql_json """ SELECT json_array(cast('{\"a\":1}' as JSON)); """
+ qt_sql_json """ SELECT json_array(cast('{\"a\":1.1}' as JSON)); """
+
+ // test with table
+ tableName = "test_query_json_array_complex"
+ sql "DROP TABLE IF EXISTS ${tableName}"
+ sql """
+ CREATE TABLE ${tableName} (
+ `k0` int(11) not null,
+ `k1` array<string> NULL,
+ `k2` map<string, string> NULL,
+ `k3` struct<name:string, age:int> NULL,
+ `k4` json NULL
+ ) ENGINE=OLAP
+ DUPLICATE KEY(`k0`)
+ COMMENT "OLAP"
+ DISTRIBUTED BY HASH(`k0`) BUCKETS 1
+ PROPERTIES (
+ "replication_allocation" = "tag.location.default: 1",
+ "in_memory" = "false",
+ "storage_format" = "V2"
+ );
+ """
+ sql "insert into ${tableName} values(1,null,null,null,null);"
+ sql "insert into ${tableName} values(2, array('a','b'), map('a','b'),
named_struct('name','a','age',1), '{\"a\":\"b\"}');"
+ sql """insert into ${tableName} values(3, array('"a"', '"b"'), map('"a"',
'"b"', '"c"', '"d"'), named_struct('name','"a"','age', 1), '{\"c\":\"d\"}');"""
+ sql """insert into ${tableName} values(4, array(1,2), map(1,2),
named_struct('name', 2, 'age',1), '{\"a\":\"b\"}');"""
+ sql """insert into ${tableName} values(5, array(1,2,3,3), map(1,2,3,4),
named_struct('name',\"a\",'age',1), '{\"a\":\"b\"}');"""
+ qt_sql3 "select json_array(k0,k1,k2,k3,k4) from ${tableName} order by k0;"
+ sql "DROP TABLE ${tableName};"
}
diff --git
a/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_insert.groovy
b/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_insert.groovy
index b5865034538..7afb9a5e6c5 100644
---
a/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_insert.groovy
+++
b/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_insert.groovy
@@ -42,4 +42,59 @@ suite("test_query_json_insert", "query,arrow_flight_sql") {
sql "insert into ${tableName} values(4,null,null);"
qt_sql1 "select json_insert('{\"id\": 0, \"time\": \"1970-01-01
00:00:00\", \"a1\": [1, 2], \"a2\": [1, 2]}', '\$.id', id, '\$.time', time,
'\$.a1[1]', k, '\$.a2[3]', k) from ${tableName} order by id;"
sql "DROP TABLE ${tableName};"
+
+ // test json_insert with complex type
+ // array
+ qt_sql_array """ SELECT json_insert('{"data": {}}', '\$.data.arr',
array('"aaa"','"bbb"')); """
+ qt_sql_array """ SELECT json_insert('{"data": {}}', '\$.data.arr',
array('aaa','bbb')); """
+ qt_sql_array """ SELECT json_insert('{"data": {}}', '\$.data.arr',
array(1,2)); """
+ qt_sql_array """ SELECT json_insert('{"data": {}}', '\$.data.arr',
array(1.1,2.2)); """
+ qt_sql_array """ SELECT json_insert('{"data": {}}', '\$.data.arr',
array(1.1,2)); """
+ qt_sql_array """ SELECT json_insert('{"data": {}}', '\$.data.arr',
array(cast(1 as decimal), cast(1.2 as decimal))); """
+ // map
+ qt_sql_map """ SELECT json_insert('{"data": {}}', '\$.data.map', map('a',
'b', 'c', 'd')); """
+ qt_sql_map """ SELECT json_insert('{"data": {}}', '\$.data.map', map('a',
1, 'c', 2)); """
+ qt_sql_map """ SELECT json_insert('{"data": {}}', '\$.data.map', map('a',
1.1, 'c', 2.2)); """
+ qt_sql_map """ SELECT json_insert('{"data": {}}', '\$.data.map', map('a',
1.1, 'c', 2)); """
+ qt_sql_map """ SELECT json_insert('{"data": {}}', '\$.data.map', map('a',
cast(1 as decimal), 'c', cast(1.2 as decimal))); """
+ // struct
+ qt_sql_struct """ SELECT json_insert('{"data": {}}', '\$.data.struct',
named_struct('name', 'a', 'age', 1)); """
+ qt_sql_struct """ SELECT json_insert('{"data": {}}', '\$.data.struct',
named_struct('name', 'a', 'age', 1.1)); """
+ qt_sql_struct """ SELECT json_insert('{"data": {}}', '\$.data.struct',
named_struct('name', 'a', 'age', cast(1 as decimal))); """
+ // json
+ qt_sql_json """ SELECT json_insert('{"data": {}}', '\$.data.json',
cast('{\"a\":\"b\"}' as JSON)); """
+ qt_sql_json """ SELECT json_insert('{"data": {}}', '\$.data.json',
cast('{\"a\":1}' as JSON)); """
+ qt_sql_json """ SELECT json_insert('{"data": {}}', '\$.data.json',
cast('{\"a\":1.1}' as JSON)); """
+
+ // test with table
+ tableName = "test_query_json_insert_complex"
+ sql "DROP TABLE IF EXISTS ${tableName}"
+ sql """
+ CREATE TABLE ${tableName} (
+ `k0` int(11) not null,
+ `k1` array<string> NULL,
+ `k2` map<string, string> NULL,
+ `k3` struct<name:string, age:int> NULL,
+ `k4` json NULL
+ ) ENGINE=OLAP
+ DUPLICATE KEY(`k0`)
+ COMMENT "OLAP"
+ DISTRIBUTED BY HASH(`k0`) BUCKETS 1
+ PROPERTIES (
+ "replication_allocation" = "tag.location.default: 1",
+ "in_memory" = "false",
+ "storage_format" = "V2"
+ );
+ """
+ sql "insert into ${tableName} values(1,null,null,null,null);"
+ sql "insert into ${tableName} values(2, array('a','b'), map('a','b'),
named_struct('name','a','age',1), '{\"a\":\"b\"}');"
+ sql """insert into ${tableName} values(3, array('"a"', '"b"'), map('"a"',
'"b"', '"c"', '"d"'), named_struct('name','"a"','age', 1), '{\"c\":\"d\"}');"""
+ sql """insert into ${tableName} values(4, array(1,2), map(1,2),
named_struct('name', 2, 'age',1), '{\"a\":\"b\"}');"""
+ sql """insert into ${tableName} values(5, array(1,2,3,3), map(1,2,3,4),
named_struct('name',\"a\",'age',1), '{\"a\":\"b\"}');"""
+ qt_sql2 """select json_insert('{"data": {}}',
+ '\$.data.array', k1,
+ '\$.data.map', k2,
+ '\$.data.struct', k3,
+ '\$.data.json', k4) from ${tableName} order by
k0;"""
+ sql "DROP TABLE ${tableName};"
}
diff --git
a/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_object.groovy
b/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_object.groovy
index 2ee0c64276c..60c08780c7c 100644
---
a/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_object.groovy
+++
b/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_object.groovy
@@ -48,4 +48,60 @@ suite("test_query_json_object", "query") {
qt_sql2 """select json_object ( CONCAT('k',t.number%30926%3000 +
0),CONCAT('k',t.number%30926%3000 + 0,t.number%1000000) ) from numbers("number"
= "2") t order by 1;"""
sql "DROP TABLE ${tableName};"
+
+ // test json_object with complex type
+ // literal cases
+ // array
+ qt_sql_array """ SELECT json_object('id', 1, 'level',
array('"aaa"','"bbb"')); """
+ qt_sql_array """ SELECT json_object('id', 1, 'level', array('aaa','bbb'));
"""
+ qt_sql_array """ SELECT json_object('id', 1, 'level', array(1,2)); """
+ qt_sql_array """ SELECT json_object('id', 1, 'level', array(1.1,2.2)); """
+ qt_sql_array """ SELECT json_object('id', 1, 'level', array(1.1,2)); """
+ qt_sql_array """ SELECT json_object('id', 1, 'level', array(cast(1 as
decimal), cast(1.2 as decimal))); """
+ // map
+ qt_sql_map """ SELECT json_object('id', 1, 'level', map('a', 'b', 'c',
'd')); """
+ qt_sql_map """ SELECT json_object('id', 1, 'level', map('a', 1, 'c', 2));
"""
+ qt_sql_map """ SELECT json_object('id', 1, 'level', map('a', 1.1, 'c',
2.2)); """
+ qt_sql_map """ SELECT json_object('id', 1, 'level', map('a', 1.1, 'c',
2)); """
+ qt_sql_map """ SELECT json_object('id', 1, 'level', map('a', cast(1 as
decimal), 'c', cast(1.2 as decimal))); """
+ // struct
+ qt_sql_struct """ SELECT json_object('id', 1, 'level',
named_struct('name', 'a', 'age', 1)); """
+ qt_sql_struct """ SELECT json_object('id', 1, 'level',
named_struct('name', 'a', 'age', 1.1)); """
+ qt_sql_struct """ SELECT json_object('id', 1, 'level',
named_struct('name', 'a', 'age', 1)); """
+ qt_sql_struct """ SELECT json_object('id', 1, 'level',
named_struct('name', 'a', 'age', 1.1)); """
+ // json
+ qt_sql_json """ SELECT json_object('id', 1, 'level', cast('{\"a\":\"b\"}'
as JSON)); """
+ qt_sql_json """ SELECT json_object('id', 1, 'level', cast('{\"a\":1}' as
JSON)); """
+ qt_sql_json """ SELECT json_object('id', 1, 'level', cast('{\"a\":1.1}' as
JSON)); """
+ qt_sql_json """ SELECT json_object('id', 1, 'level', cast('{\"a\":1.1}' as
JSON)); """
+ qt_sql_json """ SELECT json_object('id', 1, 'level', cast('{\"a\":1.1}' as
JSON)); """
+
+
+
+ tableName = "test_query_json_object_complex"
+ sql "DROP TABLE IF EXISTS ${tableName}"
+ sql """
+ CREATE TABLE test_query_json_object_complex (
+ `k0` int(11) not null,
+ `k1` array<string> NULL,
+ `k2` map<string, string> NULL,
+ `k3` struct<name:string, age:int> NULL,
+ `k4` json NULL
+ ) ENGINE=OLAP
+ DUPLICATE KEY(`k0`)
+ COMMENT "OLAP"
+ DISTRIBUTED BY HASH(`k0`) BUCKETS 1
+ PROPERTIES (
+ "replication_allocation" = "tag.location.default: 1",
+ "in_memory" = "false",
+ "storage_format" = "V2"
+ );
+ """
+ sql "insert into ${tableName} values(1,null,null,null,null);"
+ sql "insert into ${tableName} values(2, array('a','b'), map('a','b'),
named_struct('name','a','age',1), '{\"a\":\"b\"}');"
+ sql """insert into ${tableName} values(3, array('"a"', '"b"'), map('"a"',
'"b"', '"c"', '"d"'), named_struct('name','"a"','age', 1), '{\"c\":\"d\"}');"""
+ sql """insert into ${tableName} values(4, array(1,2), map(1,2),
named_struct('name', 2, 'age',1), '{\"a\":\"b\"}');"""
+ sql """insert into ${tableName} values(5, array(1,2,3,3), map(1,2,3,4),
named_struct('name',\"a\",'age',1), '{\"a\":\"b\"}');"""
+ qt_sql2 "select json_object('k0',k0,'k1',k1,'k2',k2,'k3',k3,'k4',k4) from
${tableName} order by k0;"
+
}
diff --git
a/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_replace.groovy
b/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_replace.groovy
index a870169d962..e0ffe58af29 100644
---
a/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_replace.groovy
+++
b/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_replace.groovy
@@ -65,4 +65,59 @@ suite("test_query_json_replace", "query") {
qt_sql2 "select json_replace('{\"id\": 0, \"time\": \"1970-01-01
00:00:00\", \"a1\": [1, 2], \"a2\": [1, 2]}', '\$.id', id, '\$.time', time,
'\$.a1[1]', k, '\$.a2[3]', k) from test_query_json_replace_nullable order by
id;"
sql "DROP TABLE test_query_json_replace_nullable;"
+
+ // test json_replace with complex type
+ // array
+ qt_sql_array """ SELECT json_replace('{"arr": [1,2]}', '\$.arr',
array('"aaa"','"bbb"')); """
+ qt_sql_array """ SELECT json_replace('{"arr": [1,2]}', '\$.arr',
array('aaa','bbb')); """
+ qt_sql_array """ SELECT json_replace('{"arr": [1,2]}', '\$.arr',
array(1,2)); """
+ qt_sql_array """ SELECT json_replace('{"arr": [1,2]}', '\$.arr',
array(1.1,2.2)); """
+ qt_sql_array """ SELECT json_replace('{"arr": [1,2]}', '\$.arr',
array(1.1,2)); """
+ qt_sql_array """ SELECT json_replace('{"arr": [1,2]}', '\$.arr',
array(cast(1 as decimal), cast(1.2 as decimal))); """
+ // map
+ qt_sql_map """ SELECT json_replace('{"map": {"x": "y"}}', '\$.map',
map('a', 'b', 'c', 'd')); """
+ qt_sql_map """ SELECT json_replace('{"map": {"x": "y"}}', '\$.map',
map('a', 1, 'c', 2)); """
+ qt_sql_map """ SELECT json_replace('{"map": {"x": "y"}}', '\$.map',
map('a', 1.1, 'c', 2.2)); """
+ qt_sql_map """ SELECT json_replace('{"map": {"x": "y"}}', '\$.map',
map('a', 1.1, 'c', 2)); """
+ qt_sql_map """ SELECT json_replace('{"map": {"x": "y"}}', '\$.map',
map('a', cast(1 as decimal), 'c', cast(1.2 as decimal))); """
+ // struct
+ qt_sql_struct """ SELECT json_replace('{"struct": {"name": "x", "age":
0}}', '\$.struct', named_struct('name', 'a', 'age', 1)); """
+ qt_sql_struct """ SELECT json_replace('{"struct": {"name": "x", "age":
0}}', '\$.struct', named_struct('name', 'a', 'age', 1.1)); """
+ qt_sql_struct """ SELECT json_replace('{"struct": {"name": "x", "age":
0}}', '\$.struct', named_struct('name', 'a', 'age', cast(1 as decimal))); """
+ // json
+ qt_sql_json """ SELECT json_replace('{"json": {"x": "y"}}', '\$.json',
cast('{\"a\":\"b\"}' as JSON)); """
+ qt_sql_json """ SELECT json_replace('{"json": {"x": "y"}}', '\$.json',
cast('{\"a\":1}' as JSON)); """
+ qt_sql_json """ SELECT json_replace('{"json": {"x": "y"}}', '\$.json',
cast('{\"a\":1.1}' as JSON)); """
+
+ // test with table
+ tableName = "test_query_json_replace_complex"
+ sql "DROP TABLE IF EXISTS ${tableName}"
+ sql """
+ CREATE TABLE ${tableName} (
+ `k0` int(11) not null,
+ `k1` array<string> NULL,
+ `k2` map<string, string> NULL,
+ `k3` struct<name:string, age:int> NULL,
+ `k4` json NULL
+ ) ENGINE=OLAP
+ DUPLICATE KEY(`k0`)
+ COMMENT "OLAP"
+ DISTRIBUTED BY HASH(`k0`) BUCKETS 1
+ PROPERTIES (
+ "replication_allocation" = "tag.location.default: 1",
+ "in_memory" = "false",
+ "storage_format" = "V2"
+ );
+ """
+ sql "insert into ${tableName} values(1,null,null,null,null);"
+ sql "insert into ${tableName} values(2, array('a','b'), map('a','b'),
named_struct('name','a','age',1), '{\"a\":\"b\"}');"
+ sql """insert into ${tableName} values(3, array('"a"', '"b"'), map('"a"',
'"b"', '"c"', '"d"'), named_struct('name','"a"','age', 1), '{\"c\":\"d\"}');"""
+ sql """insert into ${tableName} values(4, array(1,2), map(1,2),
named_struct('name', 2, 'age',1), '{\"a\":\"b\"}');"""
+ sql """insert into ${tableName} values(5, array(1,2,3,3), map(1,2,3,4),
named_struct('name',\"a\",'age',1), '{\"a\":\"b\"}');"""
+ qt_sql3 """select json_replace('{"data": {"array": [1], "map": {"x":"y"},
"struct": {"name":"x","age":0}, "json": {"x":"y"}}}',
+ '\$.data.array', k1,
+ '\$.data.map', k2,
+ '\$.data.struct', k3,
+ '\$.data.json', k4) from ${tableName} order by
k0;"""
+ sql "DROP TABLE ${tableName};"
}
diff --git
a/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_set.groovy
b/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_set.groovy
index 2c65ddb4104..6f04e4be88a 100644
---
a/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_set.groovy
+++
b/regression-test/suites/query_p0/sql_functions/json_function/test_query_json_set.groovy
@@ -42,4 +42,59 @@ suite("test_query_json_set", "query") {
sql "insert into ${tableName} values(4,null,null);"
qt_sql1 "select json_set('{\"id\": 0, \"time\": \"1970-01-01 00:00:00\",
\"a1\": [1, 2], \"a2\": [1, 2]}', '\$.id', id, '\$.time', time, '\$.a1[1]', k,
'\$.a2[3]', k) from ${tableName} order by id;"
sql "DROP TABLE ${tableName};"
+
+ // test json_set with complex type
+ // array
+ qt_sql_array """ SELECT json_set('{"arr": null}', '\$.arr',
array('"aaa"','"bbb"')); """
+ qt_sql_array """ SELECT json_set('{"arr": null}', '\$.arr',
array('aaa','bbb')); """
+ qt_sql_array """ SELECT json_set('{"arr": null}', '\$.arr', array(1,2));
"""
+ qt_sql_array """ SELECT json_set('{"arr": null}', '\$.arr',
array(1.1,2.2)); """
+ qt_sql_array """ SELECT json_set('{"arr": null}', '\$.arr', array(1.1,2));
"""
+ qt_sql_array """ SELECT json_set('{"arr": null}', '\$.arr', array(cast(1
as decimal), cast(1.2 as decimal))); """
+ // map
+ qt_sql_map """ SELECT json_set('{"map": null}', '\$.map', map('a', 'b',
'c', 'd')); """
+ qt_sql_map """ SELECT json_set('{"map": null}', '\$.map', map('a', 1, 'c',
2)); """
+ qt_sql_map """ SELECT json_set('{"map": null}', '\$.map', map('a', 1.1,
'c', 2.2)); """
+ qt_sql_map """ SELECT json_set('{"map": null}', '\$.map', map('a', 1.1,
'c', 2)); """
+ qt_sql_map """ SELECT json_set('{"map": null}', '\$.map', map('a', cast(1
as decimal), 'c', cast(1.2 as decimal))); """
+ // struct
+ qt_sql_struct """ SELECT json_set('{"struct": null}', '\$.struct',
named_struct('name', 'a', 'age', 1)); """
+ qt_sql_struct """ SELECT json_set('{"struct": null}', '\$.struct',
named_struct('name', 'a', 'age', 1.1)); """
+ qt_sql_struct """ SELECT json_set('{"struct": null}', '\$.struct',
named_struct('name', 'a', 'age', cast(1 as decimal))); """
+ // json
+ qt_sql_json """ SELECT json_set('{"json": null}', '\$.json',
cast('{\"a\":\"b\"}' as JSON)); """
+ qt_sql_json """ SELECT json_set('{"json": null}', '\$.json',
cast('{\"a\":1}' as JSON)); """
+ qt_sql_json """ SELECT json_set('{"json": null}', '\$.json',
cast('{\"a\":1.1}' as JSON)); """
+
+ // test with table
+ tableName = "test_query_json_set_complex"
+ sql "DROP TABLE IF EXISTS ${tableName}"
+ sql """
+ CREATE TABLE ${tableName} (
+ `k0` int(11) not null,
+ `k1` array<string> NULL,
+ `k2` map<string, string> NULL,
+ `k3` struct<name:string, age:int> NULL,
+ `k4` json NULL
+ ) ENGINE=OLAP
+ DUPLICATE KEY(`k0`)
+ COMMENT "OLAP"
+ DISTRIBUTED BY HASH(`k0`) BUCKETS 1
+ PROPERTIES (
+ "replication_allocation" = "tag.location.default: 1",
+ "in_memory" = "false",
+ "storage_format" = "V2"
+ );
+ """
+ sql "insert into ${tableName} values(1,null,null,null,null);"
+ sql "insert into ${tableName} values(2, array('a','b'), map('a','b'),
named_struct('name','a','age',1), '{\"a\":\"b\"}');"
+ sql """insert into ${tableName} values(3, array('"a"', '"b"'), map('"a"',
'"b"', '"c"', '"d"'), named_struct('name','"a"','age', 1), '{\"c\":\"d\"}');"""
+ sql """insert into ${tableName} values(4, array(1,2), map(1,2),
named_struct('name', 2, 'age',1), '{\"a\":\"b\"}');"""
+ sql """insert into ${tableName} values(5, array(1,2,3,3), map(1,2,3,4),
named_struct('name',\"a\",'age',1), '{\"a\":\"b\"}');"""
+ qt_sql2 """select json_set('{"data": {"array": null, "map": null,
"struct": null, "json": null}}',
+ '\$.data.array', k1,
+ '\$.data.map', k2,
+ '\$.data.struct', k3,
+ '\$.data.json', k4) from ${tableName} order by
k0;"""
+ sql "DROP TABLE ${tableName};"
}
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]