This is an automated email from the ASF dual-hosted git repository. lihaopeng pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/doris.git
The following commit(s) were added to refs/heads/master by this push: new 57ec11bd00d [fix](function) fix ipv4 funcs get failed error, improve an ipv6 func and exception message (#30269) 57ec11bd00d is described below commit 57ec11bd00d810f730763df518403987b34a880b Author: Chester <42577861+superdiaod...@users.noreply.github.com> AuthorDate: Sat Jan 27 21:37:44 2024 +0800 [fix](function) fix ipv4 funcs get failed error, improve an ipv6 func and exception message (#30269) --- be/src/vec/functions/function_ip.cpp | 39 ++++-- be/src/vec/functions/function_ip.h | 150 +++++++++++---------- .../ip-functions/ipv4-string-to-num-or-default.md | 10 +- .../ip-functions/ipv4-string-to-num.md | 5 +- .../ip-functions/ipv6-string-to-num.md | 5 +- .../ip-functions/ipv4-string-to-num-or-default.md | 10 +- .../ip-functions/ipv4-string-to-num.md | 5 +- .../ip-functions/ipv6-string-to-num.md | 5 +- .../data/nereids_function_p0/ip_functions.out | 9 ++ .../ip_functions/test_ip_functions.out | 9 ++ .../suites/nereids_function_p0/ip_functions.groovy | 3 + .../ip_functions/test_ip_functions.groovy | 3 + 12 files changed, 160 insertions(+), 93 deletions(-) diff --git a/be/src/vec/functions/function_ip.cpp b/be/src/vec/functions/function_ip.cpp index 700fb897b44..5e288bf9ec7 100644 --- a/be/src/vec/functions/function_ip.cpp +++ b/be/src/vec/functions/function_ip.cpp @@ -20,30 +20,41 @@ namespace doris::vectorized { void register_function_ip(SimpleFunctionFactory& factory) { + /// IPv4 convert between string and num part factory.register_function<FunctionIPv4NumToString>(); factory.register_alias(FunctionIPv4NumToString::name, "inet_ntoa"); - factory.register_function<FunctionIPv4StringToNum<IPExceptionMode::Throw>>(); - factory.register_function<FunctionIPv4StringToNum<IPExceptionMode::Default>>(); - factory.register_function<FunctionIPv4StringToNum<IPExceptionMode::Null>>(); - factory.register_alias(FunctionIPv4StringToNum<IPExceptionMode::Null>::name, "inet_aton"); + factory.register_function<FunctionIPv4StringToNum<IPConvertExceptionMode::Throw>>(); + factory.register_function<FunctionIPv4StringToNum<IPConvertExceptionMode::Default>>(); + factory.register_function<FunctionIPv4StringToNum<IPConvertExceptionMode::Null>>(); + factory.register_alias(FunctionIPv4StringToNum<IPConvertExceptionMode::Null>::name, + "inet_aton"); + + /// IPv6 convert between string and num part factory.register_function<FunctionIPv6NumToString>(); factory.register_alias(FunctionIPv6NumToString::name, "inet6_ntoa"); - factory.register_function<FunctionIPv6StringToNum<IPExceptionMode::Throw>>(); - factory.register_function<FunctionIPv6StringToNum<IPExceptionMode::Default>>(); - factory.register_function<FunctionIPv6StringToNum<IPExceptionMode::Null>>(); - factory.register_alias(FunctionIPv6StringToNum<IPExceptionMode::Null>::name, "inet6_aton"); + factory.register_function<FunctionIPv6StringToNum<IPConvertExceptionMode::Throw>>(); + factory.register_function<FunctionIPv6StringToNum<IPConvertExceptionMode::Default>>(); + factory.register_function<FunctionIPv6StringToNum<IPConvertExceptionMode::Null>>(); + factory.register_alias(FunctionIPv6StringToNum<IPConvertExceptionMode::Null>::name, + "inet6_aton"); + + /// Judge part factory.register_function<FunctionIsIPv4Compat>(); factory.register_function<FunctionIsIPv4Mapped>(); factory.register_function<FunctionIsIPString<IPv4>>(); factory.register_function<FunctionIsIPString<IPv6>>(); factory.register_function<FunctionIsIPAddressInRange>(); + + /// CIDR part factory.register_function<FunctionIPv4CIDRToRange>(); factory.register_function<FunctionIPv6CIDRToRange>(); - factory.register_function<FunctionToIP<IPExceptionMode::Throw, IPv4>>(); - factory.register_function<FunctionToIP<IPExceptionMode::Default, IPv4>>(); - factory.register_function<FunctionToIP<IPExceptionMode::Null, IPv4>>(); - factory.register_function<FunctionToIP<IPExceptionMode::Throw, IPv6>>(); - factory.register_function<FunctionToIP<IPExceptionMode::Default, IPv6>>(); - factory.register_function<FunctionToIP<IPExceptionMode::Null, IPv6>>(); + + /// Convert to IPv4/IPv6 part + factory.register_function<FunctionToIP<IPConvertExceptionMode::Throw, IPv4>>(); + factory.register_function<FunctionToIP<IPConvertExceptionMode::Default, IPv4>>(); + factory.register_function<FunctionToIP<IPConvertExceptionMode::Null, IPv4>>(); + factory.register_function<FunctionToIP<IPConvertExceptionMode::Throw, IPv6>>(); + factory.register_function<FunctionToIP<IPConvertExceptionMode::Default, IPv6>>(); + factory.register_function<FunctionToIP<IPConvertExceptionMode::Null, IPv6>>(); } } // namespace doris::vectorized \ No newline at end of file diff --git a/be/src/vec/functions/function_ip.h b/be/src/vec/functions/function_ip.h index 65075bcaa2b..98802a3ee20 100644 --- a/be/src/vec/functions/function_ip.h +++ b/be/src/vec/functions/function_ip.h @@ -128,13 +128,14 @@ public: } }; -enum class IPExceptionMode : uint8_t { Throw, Default, Null }; +/// Since IPExceptionMode means wider scope, we use more specific name here. +enum class IPConvertExceptionMode : uint8_t { Throw, Default, Null }; static inline bool tryParseIPv4(const char* pos, Int64& result_value) { return parseIPv4whole(pos, reinterpret_cast<unsigned char*>(&result_value)); } -template <IPExceptionMode exception_mode, typename ToColumn> +template <IPConvertExceptionMode exception_mode, typename ToColumn> ColumnPtr convertToIPv4(ColumnPtr column, const PaddedPODArray<UInt8>* null_map = nullptr) { const ColumnString* column_string = check_and_get_column<ColumnString>(column.get()); @@ -149,7 +150,7 @@ ColumnPtr convertToIPv4(ColumnPtr column, const PaddedPODArray<UInt8>* null_map ColumnUInt8::MutablePtr col_null_map_to; ColumnUInt8::Container* vec_null_map_to = nullptr; - if constexpr (exception_mode == IPExceptionMode::Null) { + if constexpr (exception_mode == IPConvertExceptionMode::Null) { col_null_map_to = ColumnUInt8::create(column_size, false); vec_null_map_to = &col_null_map_to->get_data(); } @@ -165,14 +166,19 @@ ColumnPtr convertToIPv4(ColumnPtr column, const PaddedPODArray<UInt8>* null_map for (size_t i = 0; i < vec_res.size(); ++i) { if (null_map && (*null_map)[i]) { + if constexpr (exception_mode == IPConvertExceptionMode::Throw) { + throw Exception( + ErrorCode::INVALID_ARGUMENT, + "Null Input, you may consider convert it to a valid default IPv4 value " + "like '0.0.0.0' first"); + } vec_res[i] = 0; prev_offset = offsets_src[i]; - if constexpr (exception_mode == IPExceptionMode::Null) { + if constexpr (exception_mode == IPConvertExceptionMode::Null) { (*vec_null_map_to)[i] = true; } continue; } - const char* src_start = reinterpret_cast<const char*>(&vec_src[prev_offset]); size_t src_length = (i < vec_res.size() - 1) ? (offsets_src[i] - prev_offset) : (vec_src.size() - prev_offset); @@ -180,11 +186,11 @@ ColumnPtr convertToIPv4(ColumnPtr column, const PaddedPODArray<UInt8>* null_map bool parse_result = tryParseIPv4(src.c_str(), vec_res[i]); if (!parse_result) { - if constexpr (exception_mode == IPExceptionMode::Throw) { + if constexpr (exception_mode == IPConvertExceptionMode::Throw) { throw Exception(ErrorCode::INVALID_ARGUMENT, "Invalid IPv4 value"); - } else if constexpr (exception_mode == IPExceptionMode::Default) { + } else if constexpr (exception_mode == IPConvertExceptionMode::Default) { vec_res[i] = 0; - } else if constexpr (exception_mode == IPExceptionMode::Null) { + } else if constexpr (exception_mode == IPConvertExceptionMode::Null) { (*vec_null_map_to)[i] = true; vec_res[i] = 0; } @@ -193,20 +199,20 @@ ColumnPtr convertToIPv4(ColumnPtr column, const PaddedPODArray<UInt8>* null_map prev_offset = offsets_src[i]; } - if constexpr (exception_mode == IPExceptionMode::Null) + if constexpr (exception_mode == IPConvertExceptionMode::Null) { return ColumnNullable::create(std::move(col_res), std::move(col_null_map_to)); - + } return col_res; } -template <IPExceptionMode exception_mode> +template <IPConvertExceptionMode exception_mode> class FunctionIPv4StringToNum : public IFunction { public: - static constexpr auto name = - exception_mode == IPExceptionMode::Throw - ? "ipv4_string_to_num" - : (exception_mode == IPExceptionMode::Default ? "ipv4_string_to_num_or_default" - : "ipv4_string_to_num_or_null"); + static constexpr auto name = exception_mode == IPConvertExceptionMode::Throw + ? "ipv4_string_to_num" + : (exception_mode == IPConvertExceptionMode::Default + ? "ipv4_string_to_num_or_default" + : "ipv4_string_to_num_or_null"); static FunctionPtr create() { return std::make_shared<FunctionIPv4StringToNum<exception_mode>>(); @@ -224,11 +230,11 @@ public: } auto result_type = std::make_shared<DataTypeInt64>(); - if constexpr (exception_mode == IPExceptionMode::Null) { + if constexpr (exception_mode == IPConvertExceptionMode::Null) { return make_nullable(result_type); } - return arguments[0]->is_nullable() ? make_nullable(result_type) : result_type; + return result_type; } bool use_default_implementation_for_nulls() const override { return false; } @@ -247,14 +253,12 @@ public: auto col_res = convertToIPv4<exception_mode, ColumnInt64>(column, null_map); - if (null_map && !col_res->is_nullable()) { - block.replace_by_position(result, - ColumnNullable::create(IColumn::mutate(col_res), - IColumn::mutate(null_map_column))); - return Status::OK(); + if (null_map && exception_mode == IPConvertExceptionMode::Null) { + block.replace_by_position( + result, ColumnNullable::create(std::move(col_res), std::move(null_map_column))); + } else { + block.replace_by_position(result, std::move(col_res)); } - - block.replace_by_position(result, col_res); return Status::OK(); } }; @@ -354,7 +358,8 @@ public: }; namespace detail { -template <IPExceptionMode exception_mode, typename ToColumn = ColumnIPv6, typename StringColumnType> +template <IPConvertExceptionMode exception_mode, typename ToColumn = ColumnIPv6, + typename StringColumnType> ColumnPtr convertToIPv6(const StringColumnType& string_column, const PaddedPODArray<UInt8>* null_map = nullptr) { if constexpr (!std::is_same_v<ToColumn, ColumnString> && @@ -369,7 +374,7 @@ ColumnPtr convertToIPv6(const StringColumnType& string_column, ColumnUInt8::MutablePtr col_null_map_to; ColumnUInt8::Container* vec_null_map_to = nullptr; - if constexpr (exception_mode == IPExceptionMode::Null) { + if constexpr (exception_mode == IPConvertExceptionMode::Null) { col_null_map_to = ColumnUInt8::create(column_size, false); vec_null_map_to = &col_null_map_to->get_data(); } @@ -430,17 +435,20 @@ ColumnPtr convertToIPv6(const StringColumnType& string_column, } if (null_map && (*null_map)[i]) { - if (exception_mode == IPExceptionMode::Throw) { - throw Exception(ErrorCode::INVALID_ARGUMENT, "Invalid IPv6 value"); - } else if (exception_mode == IPExceptionMode::Default) { + if (exception_mode == IPConvertExceptionMode::Throw) { + throw Exception( + ErrorCode::INVALID_ARGUMENT, + "Null Input, you may consider convert it to a valid default IPv6 value " + "like '::' first"); + } else if (exception_mode == IPConvertExceptionMode::Default) { std::fill_n(&vec_res[out_offset], offset_inc, 0); } else { std::fill_n(&vec_res[out_offset], offset_inc, 0); (*vec_null_map_to)[i] = true; - if constexpr (std::is_same_v<ToColumn, ColumnString>) { - auto* column_string = assert_cast<ColumnString*>(col_res.get()); - column_string->get_offsets().push_back((i + 1) * IPV6_BINARY_LENGTH); - } + } + if constexpr (std::is_same_v<ToColumn, ColumnString>) { + auto* column_string = assert_cast<ColumnString*>(col_res.get()); + column_string->get_offsets().push_back((i + 1) * IPV6_BINARY_LENGTH); } src_offset = src_next_offset; continue; @@ -473,7 +481,7 @@ ColumnPtr convertToIPv6(const StringColumnType& string_column, col_res->insert_data(reinterpret_cast<const char*>(res_value), IPV6_BINARY_LENGTH); } } else { - if (exception_mode == IPExceptionMode::Throw) { + if (exception_mode == IPConvertExceptionMode::Throw) { throw Exception(ErrorCode::INVALID_ARGUMENT, "Invalid IPv6 value"); } std::fill_n(&vec_res[out_offset], offset_inc, 0); @@ -481,21 +489,21 @@ ColumnPtr convertToIPv6(const StringColumnType& string_column, auto* column_string = assert_cast<ColumnString*>(col_res.get()); column_string->get_offsets().push_back((i + 1) * IPV6_BINARY_LENGTH); } - if constexpr (exception_mode == IPExceptionMode::Null) { + if constexpr (exception_mode == IPConvertExceptionMode::Null) { (*vec_null_map_to)[i] = true; } } src_offset = src_next_offset; } - if constexpr (exception_mode == IPExceptionMode::Null) { + if constexpr (exception_mode == IPConvertExceptionMode::Null) { return ColumnNullable::create(std::move(col_res), std::move(col_null_map_to)); } return col_res; } } // namespace detail -template <IPExceptionMode exception_mode, typename ToColumn = ColumnIPv6> +template <IPConvertExceptionMode exception_mode, typename ToColumn = ColumnIPv6> ColumnPtr convertToIPv6(ColumnPtr column, const PaddedPODArray<UInt8>* null_map = nullptr) { if (const auto* column_input_string = check_and_get_column<ColumnString>(column.get())) { auto result = @@ -507,14 +515,14 @@ ColumnPtr convertToIPv6(ColumnPtr column, const PaddedPODArray<UInt8>* null_map } } -template <IPExceptionMode exception_mode> +template <IPConvertExceptionMode exception_mode> class FunctionIPv6StringToNum : public IFunction { public: - static constexpr auto name = - exception_mode == IPExceptionMode::Throw - ? "ipv6_string_to_num" - : (exception_mode == IPExceptionMode::Default ? "ipv6_string_to_num_or_default" - : "ipv6_string_to_num_or_null"); + static constexpr auto name = exception_mode == IPConvertExceptionMode::Throw + ? "ipv6_string_to_num" + : (exception_mode == IPConvertExceptionMode::Default + ? "ipv6_string_to_num_or_default" + : "ipv6_string_to_num_or_null"); static FunctionPtr create() { return std::make_shared<FunctionIPv6StringToNum<exception_mode>>(); @@ -535,7 +543,7 @@ public: auto result_type = std::make_shared<DataTypeString>(); - if constexpr (exception_mode == IPExceptionMode::Null) { + if constexpr (exception_mode == IPConvertExceptionMode::Null) { return make_nullable(result_type); } @@ -551,22 +559,18 @@ public: if (column->is_nullable()) { const auto* column_nullable = assert_cast<const ColumnNullable*>(column.get()); column = column_nullable->get_nested_column_ptr(); - if constexpr (exception_mode == IPExceptionMode::Null) { - null_map_column = column_nullable->get_null_map_column_ptr(); - null_map = &column_nullable->get_null_map_data(); - } + null_map_column = column_nullable->get_null_map_column_ptr(); + null_map = &column_nullable->get_null_map_data(); } auto col_res = convertToIPv6<exception_mode, ColumnString>(column, null_map); - if (null_map && !col_res->is_nullable()) { - block.replace_by_position(result, - ColumnNullable::create(IColumn::mutate(col_res), - IColumn::mutate(null_map_column))); - return Status::OK(); + if (null_map && exception_mode == IPConvertExceptionMode::Null) { + block.replace_by_position( + result, ColumnNullable::create(std::move(col_res), std::move(null_map_column))); + } else { + block.replace_by_position(result, std::move(col_res)); } - - block.replace_by_position(result, col_res); return Status::OK(); } }; @@ -985,22 +989,22 @@ private: } }; -template <IPExceptionMode exception_mode, typename Type> +template <IPConvertExceptionMode exception_mode, typename Type> inline constexpr auto to_ip_func_name() { if constexpr (std::is_same_v<Type, IPv4>) { - return exception_mode == IPExceptionMode::Throw + return exception_mode == IPConvertExceptionMode::Throw ? "to_ipv4" - : (exception_mode == IPExceptionMode::Default ? "to_ipv4_or_default" - : "to_ipv4_or_null"); + : (exception_mode == IPConvertExceptionMode::Default ? "to_ipv4_or_default" + : "to_ipv4_or_null"); } else { - return exception_mode == IPExceptionMode::Throw + return exception_mode == IPConvertExceptionMode::Throw ? "to_ipv6" - : (exception_mode == IPExceptionMode::Default ? "to_ipv6_or_default" - : "to_ipv6_or_null"); + : (exception_mode == IPConvertExceptionMode::Default ? "to_ipv6_or_default" + : "to_ipv6_or_null"); } } -template <IPExceptionMode exception_mode, typename Type> +template <IPConvertExceptionMode exception_mode, typename Type> class FunctionToIP : public IFunction { static_assert(std::is_same_v<Type, IPv4> || std::is_same_v<Type, IPv6>); @@ -1028,7 +1032,7 @@ public: result_type = std::make_shared<DataTypeIPv6>(); } - if constexpr (exception_mode == IPExceptionMode::Null) { + if constexpr (exception_mode == IPConvertExceptionMode::Null) { return make_nullable(result_type); } else { return result_type; @@ -1062,11 +1066,11 @@ public: for (size_t i = 0; i < input_rows_count; ++i) { if (addr_null_map && (*addr_null_map)[i]) { - if constexpr (exception_mode == IPExceptionMode::Throw) { + if constexpr (exception_mode == IPConvertExceptionMode::Throw) { throw Exception(ErrorCode::INVALID_ARGUMENT, "The arguments of function {} must be String, not NULL", get_name()); - } else if constexpr (exception_mode == IPExceptionMode::Default) { + } else if constexpr (exception_mode == IPConvertExceptionMode::Default) { col_res_data[i] = 0; // '0.0.0.0' or '::' continue; } else { @@ -1081,10 +1085,10 @@ public: if (IPv4Value::from_string(ipv4_val, ipv4_str.data, ipv4_str.size)) { col_res_data[i] = ipv4_val; } else { - if constexpr (exception_mode == IPExceptionMode::Throw) { + if constexpr (exception_mode == IPConvertExceptionMode::Throw) { throw Exception(ErrorCode::INVALID_ARGUMENT, "Invalid IPv4 value '{}'", ipv4_str.to_string_view()); - } else if constexpr (exception_mode == IPExceptionMode::Default) { + } else if constexpr (exception_mode == IPConvertExceptionMode::Default) { col_res_data[i] = 0; // '0.0.0.0' } else { res_null_map_data[i] = 1; @@ -1096,19 +1100,19 @@ public: if (IPv6Value::from_string(ipv6_val, ipv6_str.data, ipv6_str.size)) { col_res_data[i] = ipv6_val; } else { - if constexpr (exception_mode == IPExceptionMode::Throw) { + if constexpr (exception_mode == IPConvertExceptionMode::Throw) { throw Exception(ErrorCode::INVALID_ARGUMENT, "Invalid IPv6 value '{}'", ipv6_str.to_string_view()); - } else if constexpr (exception_mode == IPExceptionMode::Default) { + } else if constexpr (exception_mode == IPConvertExceptionMode::Default) { col_res_data[i] = 0; // '::' - } else if constexpr (exception_mode == IPExceptionMode::Null) { + } else if constexpr (exception_mode == IPConvertExceptionMode::Null) { res_null_map_data[i] = 1; } } } } - if constexpr (exception_mode == IPExceptionMode::Null) { + if constexpr (exception_mode == IPConvertExceptionMode::Null) { block.replace_by_position( result, ColumnNullable::create(std::move(col_res), std::move(res_null_map))); } else { diff --git a/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num-or-default.md b/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num-or-default.md index 8400b1dc23b..880cda28a54 100644 --- a/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num-or-default.md +++ b/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num-or-default.md @@ -40,7 +40,7 @@ Takes a string containing an IPv4 address in the format A.B.C.D (dot-separated n ### notice -`will return 0 if the input parameter is invalid ipv4 value` +`will return 0 if the input parameter is invalid ipv4 value or NULL` ### example ``` @@ -62,6 +62,14 @@ mysql> select str, ipv4_string_to_num_or_default(str) from ipv4_str; | invalid | 0 | +-----------------+------------------------------------+ 4 rows in set (0.01 sec) + +mysql> select addr_src, ipv4_string_to_num_or_default(addr_src) from ipv4_string_test where addr_src is null; ++----------+-----------------------------------------+ +| addr_src | ipv4_string_to_num_or_default(addr_src) | ++----------+-----------------------------------------+ +| NULL | 0 | ++----------+-----------------------------------------+ +1 row in set (0.09 sec) ``` ### keywords diff --git a/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num.md b/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num.md index 7c5154943eb..ed69ede2860 100644 --- a/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num.md +++ b/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num.md @@ -40,7 +40,7 @@ Takes a string containing an IPv4 address in the format A.B.C.D (dot-separated n ### notice -`will return an error if the input string is not a valid IPv4 address` +`will return an error if the input string is not a valid IPv4 address or NULL` ### example ``` @@ -54,6 +54,9 @@ mysql> select ipv4_string_to_num('192.168.0.1'); mysql> select ipv4_string_to_num('invalid'); ERROR 1105 (HY000): errCode = 2, detailMessage = (172.17.0.2)[CANCELLED][INVALID_ARGUMENT][E33] Invalid IPv4 value + +mysql> select addr_src, ipv4_string_to_num(addr_src) from ipv4_string_test where addr_src is null; +ERROR 1105 (HY000): errCode = 2, detailMessage = (172.17.0.2)[CANCELLED][E33] Null Input, you may consider convert it to a valid default IPv4 value like '0.0.0.0' first ``` ### keywords diff --git a/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv6-string-to-num.md b/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv6-string-to-num.md index c9d1530549f..68f7738d04f 100644 --- a/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv6-string-to-num.md +++ b/docs/en/docs/sql-manual/sql-functions/ip-functions/ipv6-string-to-num.md @@ -41,7 +41,7 @@ If the input string contains a valid IPv4 address, returns its IPv6 equivalent. ### notice -`will return an error if the input string is not a valid IP address` +`will return an error if the input string is not a valid IP address or NULL` ### example ``` @@ -63,6 +63,9 @@ mysql> select hex(ipv6_string_to_num('192.168.0.1')); mysql> select hex(ipv6_string_to_num('notaaddress')); ERROR 1105 (HY000): errCode = 2, detailMessage = (172.17.0.2)[CANCELLED][E33] Invalid IPv6 value + +mysql> select addr_src, hex(ipv6_string_to_num(addr_src)) from ipv4_string_test where addr_src is null; +ERROR 1105 (HY000): errCode = 2, detailMessage = (172.17.0.2)[CANCELLED][E33] Null Input, you may consider convert it to a valid default IPv6 value like '::' first ``` ### keywords diff --git a/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num-or-default.md b/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num-or-default.md index 42fa8174639..033440108e0 100644 --- a/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num-or-default.md +++ b/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num-or-default.md @@ -40,7 +40,7 @@ IPV4_STRING_TO_NUM_OR_DEFAULT ### notice -`如果输入字符串不是有效的 IPv4 地址,将返回0` +`如果输入字符串不是有效的 IPv4 地址或者NULL,将返回0` ### example ``` @@ -62,6 +62,14 @@ mysql> select str, ipv4_string_to_num_or_default(str) from ipv4_str; | invalid | 0 | +-----------------+------------------------------------+ 4 rows in set (0.01 sec) + +mysql> select addr_src, ipv4_string_to_num_or_default(addr_src) from ipv4_string_test where addr_src is null; ++----------+-----------------------------------------+ +| addr_src | ipv4_string_to_num_or_default(addr_src) | ++----------+-----------------------------------------+ +| NULL | 0 | ++----------+-----------------------------------------+ +1 row in set (0.09 sec) ``` ### keywords diff --git a/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num.md b/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num.md index c2d42c1e004..e7cae9a3023 100644 --- a/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num.md +++ b/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv4-string-to-num.md @@ -40,7 +40,7 @@ IPV4_STRING_TO_NUM ### notice -`如果输入字符串不是有效的 IPv4 地址,将返回错误` +`如果输入字符串不是有效的 IPv4 地址或者NULL,将返回错误` ### example ``` @@ -54,6 +54,9 @@ mysql> select ipv4_string_to_num('192.168.0.1'); mysql> SELECT ipv4_string_to_num('192.168'); ERROR 1105 (HY000): errCode = 2, detailMessage = (172.17.0.2)[CANCELLED][INVALID_ARGUMENT][E33] Invalid IPv4 value + +mysql> select addr_src, ipv4_string_to_num(addr_src) from ipv4_string_test where addr_src is null; +ERROR 1105 (HY000): errCode = 2, detailMessage = (172.17.0.2)[CANCELLED][E33] Null Input, you may consider convert it to a valid default IPv4 value like '0.0.0.0' first ``` ### keywords diff --git a/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv6-string-to-num.md b/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv6-string-to-num.md index a02ae6374d5..8f38b86ed1a 100644 --- a/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv6-string-to-num.md +++ b/docs/zh-CN/docs/sql-manual/sql-functions/ip-functions/ipv6-string-to-num.md @@ -41,7 +41,7 @@ IPv6NumToString 的反向函数,它接受一个 IP 地址字符串并返回二 ### notice -`如果输入非法的IP地址,会抛出异常` +`如果输入非法的IP地址或者NULL,会抛出异常` ### example ``` @@ -63,6 +63,9 @@ mysql> select hex(ipv6_string_to_num('192.168.0.1')); mysql> select hex(ipv6_string_to_num('notaaddress')); ERROR 1105 (HY000): errCode = 2, detailMessage = (172.17.0.2)[CANCELLED][E33] Invalid IPv6 value + +mysql> select addr_src, hex(ipv6_string_to_num(addr_src)) from ipv4_string_test where addr_src is null; +ERROR 1105 (HY000): errCode = 2, detailMessage = (172.17.0.2)[CANCELLED][E33] Null Input, you may consider convert it to a valid default IPv6 value like '::' first ``` ### keywords diff --git a/regression-test/data/nereids_function_p0/ip_functions.out b/regression-test/data/nereids_function_p0/ip_functions.out index a89ca34fe60..44b8aa9b5c9 100644 --- a/regression-test/data/nereids_function_p0/ip_functions.out +++ b/regression-test/data/nereids_function_p0/ip_functions.out @@ -32,6 +32,15 @@ -- !ip11 -- 0 +-- !ip11_1 -- +2130706433 + +-- !ip11_2 -- +0 + +-- !ip11_3 -- +0 + -- !ip12 -- 3232235521 diff --git a/regression-test/data/query_p0/sql_functions/ip_functions/test_ip_functions.out b/regression-test/data/query_p0/sql_functions/ip_functions/test_ip_functions.out index 569dc78a1e0..6bdc72df39f 100644 --- a/regression-test/data/query_p0/sql_functions/ip_functions/test_ip_functions.out +++ b/regression-test/data/query_p0/sql_functions/ip_functions/test_ip_functions.out @@ -19,6 +19,15 @@ -- !sql -- 0 +-- !sql -- +2130706433 + +-- !sql -- +0 + +-- !sql -- +0 + -- !sql -- 3232235521 diff --git a/regression-test/suites/nereids_function_p0/ip_functions.groovy b/regression-test/suites/nereids_function_p0/ip_functions.groovy index 98a2574e62f..8fe5ca49dd3 100644 --- a/regression-test/suites/nereids_function_p0/ip_functions.groovy +++ b/regression-test/suites/nereids_function_p0/ip_functions.groovy @@ -30,6 +30,9 @@ suite("ip_functions") { qt_ip9 "SELECT ipv4_string_to_num('127.0.0.1');" qt_ip10 "SELECT ipv4_string_to_num_or_null('');" qt_ip11 "SELECT ipv4_string_to_num_or_default('');" + qt_ip11_1 "SELECT ipv4_string_to_num_or_default('127.0.0.1');" + qt_ip11_2 "SELECT ipv4_string_to_num_or_default('abc');" + qt_ip11_3 "SELECT ipv4_string_to_num_or_default(NULL);" qt_ip12 "SELECT inet_aton('192.168.0.1');" qt_ip12_1 "SELECT inet_aton('192.168');" qt_ip12_2 "SELECT inet_aton('');" diff --git a/regression-test/suites/query_p0/sql_functions/ip_functions/test_ip_functions.groovy b/regression-test/suites/query_p0/sql_functions/ip_functions/test_ip_functions.groovy index 5cbf59ac36c..64074ec2e88 100644 --- a/regression-test/suites/query_p0/sql_functions/ip_functions/test_ip_functions.groovy +++ b/regression-test/suites/query_p0/sql_functions/ip_functions/test_ip_functions.groovy @@ -25,6 +25,9 @@ suite("test_ip_functions", "arrow_flight_sql") { qt_sql "SELECT ipv4_string_to_num('127.0.0.1');" qt_sql "SELECT ipv4_string_to_num_or_null('');" qt_sql "SELECT ipv4_string_to_num_or_default('');" + qt_sql "SELECT ipv4_string_to_num_or_default('127.0.0.1');" + qt_sql "SELECT ipv4_string_to_num_or_default('abc');" + qt_sql "SELECT ipv4_string_to_num_or_default(NULL);" qt_sql "SELECT inet_aton('192.168.0.1');" qt_sql "SELECT inet_aton('192.168');" qt_sql "SELECT inet_aton('');" --------------------------------------------------------------------- To unsubscribe, e-mail: commits-unsubscr...@doris.apache.org For additional commands, e-mail: commits-h...@doris.apache.org