[feature](function) Support SHA family functions (#24342)
This commit is contained in:
118
be/src/util/sha.cpp
Normal file
118
be/src/util/sha.cpp
Normal file
@ -0,0 +1,118 @@
|
||||
// Licensed to the Apache Software Foundation (ASF) under one
|
||||
// or more contributor license agreements. See the NOTICE file
|
||||
// distributed with this work for additional information
|
||||
// regarding copyright ownership. The ASF licenses this file
|
||||
// to you under the Apache License, Version 2.0 (the
|
||||
// "License"); you may not use this file except in compliance
|
||||
// with the License. You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing,
|
||||
// software distributed under the License is distributed on an
|
||||
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
// KIND, either express or implied. See the License for the
|
||||
// specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
#include "util/sha.h"
|
||||
|
||||
#include <openssl/sha.h>
|
||||
|
||||
#include <string_view>
|
||||
|
||||
namespace doris {
|
||||
|
||||
constexpr static char dig_vec_lower[] = "0123456789abcdef";
|
||||
|
||||
void SHA1Digest::reset(const void* data, size_t length) {
|
||||
SHA1_Init(&_sha_ctx);
|
||||
SHA1_Update(&_sha_ctx, data, length);
|
||||
}
|
||||
|
||||
std::string_view SHA1Digest::digest() {
|
||||
unsigned char buf[SHA_DIGEST_LENGTH];
|
||||
SHA1_Final(buf, &_sha_ctx);
|
||||
|
||||
char* to = _reuse_hex;
|
||||
for (int i = 0; i < SHA_DIGEST_LENGTH; ++i) {
|
||||
*to++ = dig_vec_lower[buf[i] >> 4];
|
||||
*to++ = dig_vec_lower[buf[i] & 0x0F];
|
||||
}
|
||||
|
||||
return std::string_view {_reuse_hex, _reuse_hex + 2 * SHA_DIGEST_LENGTH};
|
||||
}
|
||||
|
||||
void SHA224Digest::reset(const void* data, size_t length) {
|
||||
SHA224_Init(&_sha224_ctx);
|
||||
SHA224_Update(&_sha224_ctx, data, length);
|
||||
}
|
||||
|
||||
std::string_view SHA224Digest::digest() {
|
||||
unsigned char buf[SHA224_DIGEST_LENGTH];
|
||||
SHA224_Final(buf, &_sha224_ctx);
|
||||
|
||||
char* to = _reuse_hex;
|
||||
for (int i = 0; i < SHA224_DIGEST_LENGTH; ++i) {
|
||||
*to++ = dig_vec_lower[buf[i] >> 4];
|
||||
*to++ = dig_vec_lower[buf[i] & 0x0F];
|
||||
}
|
||||
|
||||
return std::string_view {_reuse_hex, _reuse_hex + 2 * SHA224_DIGEST_LENGTH};
|
||||
}
|
||||
|
||||
void SHA256Digest::reset(const void* data, size_t length) {
|
||||
SHA256_Init(&_sha256_ctx);
|
||||
SHA256_Update(&_sha256_ctx, data, length);
|
||||
}
|
||||
|
||||
std::string_view SHA256Digest::digest() {
|
||||
unsigned char buf[SHA256_DIGEST_LENGTH];
|
||||
SHA256_Final(buf, &_sha256_ctx);
|
||||
|
||||
char* to = _reuse_hex;
|
||||
for (int i = 0; i < SHA256_DIGEST_LENGTH; ++i) {
|
||||
*to++ = dig_vec_lower[buf[i] >> 4];
|
||||
*to++ = dig_vec_lower[buf[i] & 0x0F];
|
||||
}
|
||||
|
||||
return std::string_view {_reuse_hex, _reuse_hex + 2 * SHA256_DIGEST_LENGTH};
|
||||
}
|
||||
|
||||
void SHA384Digest::reset(const void* data, size_t length) {
|
||||
SHA384_Init(&_sha384_ctx);
|
||||
SHA384_Update(&_sha384_ctx, data, length);
|
||||
}
|
||||
|
||||
std::string_view SHA384Digest::digest() {
|
||||
unsigned char buf[SHA384_DIGEST_LENGTH];
|
||||
SHA384_Final(buf, &_sha384_ctx);
|
||||
|
||||
char* to = _reuse_hex;
|
||||
for (int i = 0; i < SHA384_DIGEST_LENGTH; ++i) {
|
||||
*to++ = dig_vec_lower[buf[i] >> 4];
|
||||
*to++ = dig_vec_lower[buf[i] & 0x0F];
|
||||
}
|
||||
|
||||
return std::string_view {_reuse_hex, _reuse_hex + 2 * SHA384_DIGEST_LENGTH};
|
||||
}
|
||||
|
||||
void SHA512Digest::reset(const void* data, size_t length) {
|
||||
SHA512_Init(&_sha512_ctx);
|
||||
SHA512_Update(&_sha512_ctx, data, length);
|
||||
}
|
||||
|
||||
std::string_view SHA512Digest::digest() {
|
||||
unsigned char buf[SHA512_DIGEST_LENGTH];
|
||||
SHA512_Final(buf, &_sha512_ctx);
|
||||
|
||||
char* to = _reuse_hex;
|
||||
for (int i = 0; i < SHA512_DIGEST_LENGTH; ++i) {
|
||||
*to++ = dig_vec_lower[buf[i] >> 4];
|
||||
*to++ = dig_vec_lower[buf[i] & 0x0F];
|
||||
}
|
||||
|
||||
return std::string_view {_reuse_hex, _reuse_hex + 2 * SHA512_DIGEST_LENGTH};
|
||||
}
|
||||
|
||||
} // namespace doris
|
||||
75
be/src/util/sha.h
Normal file
75
be/src/util/sha.h
Normal file
@ -0,0 +1,75 @@
|
||||
// Licensed to the Apache Software Foundation (ASF) under one
|
||||
// or more contributor license agreements. See the NOTICE file
|
||||
// distributed with this work for additional information
|
||||
// regarding copyright ownership. The ASF licenses this file
|
||||
// to you under the Apache License, Version 2.0 (the
|
||||
// "License"); you may not use this file except in compliance
|
||||
// with the License. You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing,
|
||||
// software distributed under the License is distributed on an
|
||||
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
// KIND, either express or implied. See the License for the
|
||||
// specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <openssl/sha.h>
|
||||
|
||||
#include <string_view>
|
||||
|
||||
namespace doris {
|
||||
|
||||
class SHA1Digest {
|
||||
public:
|
||||
void reset(const void* data, size_t length);
|
||||
std::string_view digest();
|
||||
|
||||
private:
|
||||
SHA_CTX _sha_ctx;
|
||||
char _reuse_hex[2 * SHA_DIGEST_LENGTH];
|
||||
};
|
||||
|
||||
class SHA224Digest {
|
||||
public:
|
||||
void reset(const void* data, size_t length);
|
||||
std::string_view digest();
|
||||
|
||||
private:
|
||||
SHA256_CTX _sha224_ctx;
|
||||
char _reuse_hex[2 * SHA224_DIGEST_LENGTH];
|
||||
};
|
||||
|
||||
class SHA256Digest {
|
||||
public:
|
||||
void reset(const void* data, size_t length);
|
||||
std::string_view digest();
|
||||
|
||||
private:
|
||||
SHA256_CTX _sha256_ctx;
|
||||
char _reuse_hex[2 * SHA256_DIGEST_LENGTH];
|
||||
};
|
||||
|
||||
class SHA384Digest {
|
||||
public:
|
||||
void reset(const void* data, size_t length);
|
||||
std::string_view digest();
|
||||
|
||||
private:
|
||||
SHA512_CTX _sha384_ctx;
|
||||
char _reuse_hex[2 * SHA384_DIGEST_LENGTH];
|
||||
};
|
||||
|
||||
class SHA512Digest {
|
||||
public:
|
||||
void reset(const void* data, size_t length);
|
||||
std::string_view digest();
|
||||
|
||||
private:
|
||||
SHA512_CTX _sha512_ctx;
|
||||
char _reuse_hex[2 * SHA512_DIGEST_LENGTH];
|
||||
};
|
||||
} // namespace doris
|
||||
@ -972,7 +972,6 @@ void register_function_string(SimpleFunctionFactory& factory) {
|
||||
factory.register_function<FunctionFromBase64>();
|
||||
factory.register_function<FunctionSplitPart>();
|
||||
factory.register_function<FunctionSplitByString>();
|
||||
factory.register_function<FunctionStringMd5AndSM3<MD5Sum>>();
|
||||
factory.register_function<FunctionSubstringIndex>();
|
||||
factory.register_function<FunctionExtractURLParameter>();
|
||||
factory.register_function<FunctionStringParseUrl>();
|
||||
@ -980,7 +979,10 @@ void register_function_string(SimpleFunctionFactory& factory) {
|
||||
factory.register_function<FunctionMoneyFormat<MoneyFormatInt64Impl>>();
|
||||
factory.register_function<FunctionMoneyFormat<MoneyFormatInt128Impl>>();
|
||||
factory.register_function<FunctionMoneyFormat<MoneyFormatDecimalImpl>>();
|
||||
factory.register_function<FunctionStringMd5AndSM3<SM3Sum>>();
|
||||
factory.register_function<FunctionStringDigestOneArg<SM3Sum>>();
|
||||
factory.register_function<FunctionStringDigestOneArg<MD5Sum>>();
|
||||
factory.register_function<FunctionStringDigestSHA1>();
|
||||
factory.register_function<FunctionStringDigestSHA2>();
|
||||
factory.register_function<FunctionReplace>();
|
||||
factory.register_function<FunctionMask>();
|
||||
factory.register_function<FunctionMaskPartial<true>>();
|
||||
@ -993,9 +995,10 @@ void register_function_string(SimpleFunctionFactory& factory) {
|
||||
factory.register_alias(SubstringUtil::name, "substr");
|
||||
factory.register_alias(FunctionToLower::name, "lcase");
|
||||
factory.register_alias(FunctionToUpper::name, "ucase");
|
||||
factory.register_alias(FunctionStringMd5AndSM3<MD5Sum>::name, "md5");
|
||||
factory.register_alias(FunctionStringDigestOneArg<MD5Sum>::name, "md5");
|
||||
factory.register_alias(FunctionStringUTF8Length::name, "character_length");
|
||||
factory.register_alias(FunctionStringMd5AndSM3<SM3Sum>::name, "sm3");
|
||||
factory.register_alias(FunctionStringDigestOneArg<SM3Sum>::name, "sm3");
|
||||
factory.register_alias(FunctionStringDigestSHA1::name, "sha");
|
||||
|
||||
/// @TEMPORARY: for be_exec_version=2
|
||||
factory.register_alternative_function<FunctionStringEltOld>();
|
||||
|
||||
@ -41,6 +41,7 @@
|
||||
#include "runtime/decimalv2_value.h"
|
||||
#include "runtime/runtime_state.h"
|
||||
#include "runtime/string_search.hpp"
|
||||
#include "util/sha.h"
|
||||
#include "util/string_util.h"
|
||||
#include "util/utf8_check.h"
|
||||
#include "vec/aggregate_functions/aggregate_function.h"
|
||||
@ -1980,10 +1981,10 @@ struct MD5Sum {
|
||||
};
|
||||
|
||||
template <typename Impl>
|
||||
class FunctionStringMd5AndSM3 : public IFunction {
|
||||
class FunctionStringDigestOneArg : public IFunction {
|
||||
public:
|
||||
static constexpr auto name = Impl::name;
|
||||
static FunctionPtr create() { return std::make_shared<FunctionStringMd5AndSM3>(); }
|
||||
static FunctionPtr create() { return std::make_shared<FunctionStringDigestOneArg>(); }
|
||||
String get_name() const override { return name; }
|
||||
size_t get_number_of_arguments() const override { return 0; }
|
||||
bool is_variadic() const override { return true; }
|
||||
@ -1991,7 +1992,6 @@ public:
|
||||
DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
|
||||
return std::make_shared<DataTypeString>();
|
||||
}
|
||||
bool use_default_implementation_for_nulls() const override { return true; }
|
||||
|
||||
Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
|
||||
size_t result, size_t input_rows_count) override {
|
||||
@ -2045,6 +2045,107 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
class FunctionStringDigestSHA1 : public IFunction {
|
||||
public:
|
||||
static constexpr auto name = "sha1";
|
||||
static FunctionPtr create() { return std::make_shared<FunctionStringDigestSHA1>(); }
|
||||
String get_name() const override { return name; }
|
||||
size_t get_number_of_arguments() const override { return 1; }
|
||||
bool is_variadic() const override { return true; }
|
||||
|
||||
DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
|
||||
return std::make_shared<DataTypeString>();
|
||||
}
|
||||
|
||||
Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
|
||||
size_t result, size_t input_rows_count) override {
|
||||
DCHECK_EQ(arguments.size(), 1);
|
||||
|
||||
ColumnPtr str_col = block.get_by_position(arguments[0]).column;
|
||||
auto& data = assert_cast<const ColumnString*>(str_col.get())->get_chars();
|
||||
auto& offset = assert_cast<const ColumnString*>(str_col.get())->get_offsets();
|
||||
|
||||
auto res_col = ColumnString::create();
|
||||
auto& res_data = res_col->get_chars();
|
||||
auto& res_offset = res_col->get_offsets();
|
||||
res_offset.resize(input_rows_count);
|
||||
|
||||
SHA1Digest digest;
|
||||
for (size_t i = 0; i < input_rows_count; ++i) {
|
||||
int size = offset[i] - offset[i - 1];
|
||||
digest.reset(&data[offset[i - 1]], size);
|
||||
std::string_view ans = digest.digest();
|
||||
|
||||
StringOP::push_value_string(ans, i, res_data, res_offset);
|
||||
}
|
||||
|
||||
block.replace_by_position(result, std::move(res_col));
|
||||
return Status::OK();
|
||||
}
|
||||
};
|
||||
|
||||
class FunctionStringDigestSHA2 : public IFunction {
|
||||
public:
|
||||
static constexpr auto name = "sha2";
|
||||
static FunctionPtr create() { return std::make_shared<FunctionStringDigestSHA2>(); }
|
||||
String get_name() const override { return name; }
|
||||
size_t get_number_of_arguments() const override { return 2; }
|
||||
bool is_variadic() const override { return true; }
|
||||
|
||||
DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
|
||||
return std::make_shared<DataTypeString>();
|
||||
}
|
||||
|
||||
Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
|
||||
size_t result, size_t input_rows_count) override {
|
||||
DCHECK(!is_column_const(*block.get_by_position(arguments[0]).column));
|
||||
|
||||
ColumnPtr str_col = block.get_by_position(arguments[0]).column;
|
||||
auto& data = assert_cast<const ColumnString*>(str_col.get())->get_chars();
|
||||
auto& offset = assert_cast<const ColumnString*>(str_col.get())->get_offsets();
|
||||
|
||||
[[maybe_unused]] const auto& [right_column, right_const] =
|
||||
unpack_if_const(block.get_by_position(arguments[1]).column);
|
||||
auto digest_length = assert_cast<const ColumnInt32*>(right_column.get())->get_data()[0];
|
||||
|
||||
auto res_col = ColumnString::create();
|
||||
auto& res_data = res_col->get_chars();
|
||||
auto& res_offset = res_col->get_offsets();
|
||||
res_offset.resize(input_rows_count);
|
||||
|
||||
if (digest_length == 224) {
|
||||
execute_base<SHA224Digest>(data, offset, input_rows_count, res_data, res_offset);
|
||||
} else if (digest_length == 256) {
|
||||
execute_base<SHA256Digest>(data, offset, input_rows_count, res_data, res_offset);
|
||||
} else if (digest_length == 384) {
|
||||
execute_base<SHA384Digest>(data, offset, input_rows_count, res_data, res_offset);
|
||||
} else if (digest_length == 512) {
|
||||
execute_base<SHA512Digest>(data, offset, input_rows_count, res_data, res_offset);
|
||||
} else {
|
||||
return Status::InvalidArgument(
|
||||
"sha2's digest length only support 224/256/384/512 but meet {}", digest_length);
|
||||
}
|
||||
|
||||
block.replace_by_position(result, std::move(res_col));
|
||||
return Status::OK();
|
||||
}
|
||||
|
||||
private:
|
||||
template <typename T>
|
||||
void execute_base(const ColumnString::Chars& data, const ColumnString::Offsets& offset,
|
||||
int input_rows_count, ColumnString::Chars& res_data,
|
||||
ColumnString::Offsets& res_offset) {
|
||||
T digest;
|
||||
for (size_t i = 0; i < input_rows_count; ++i) {
|
||||
int size = offset[i] - offset[i - 1];
|
||||
digest.reset(&data[offset[i - 1]], size);
|
||||
std::string_view ans = digest.digest();
|
||||
|
||||
StringOP::push_value_string(ans, i, res_data, res_offset);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
class FunctionExtractURLParameter : public IFunction {
|
||||
public:
|
||||
static constexpr auto name = "extract_url_parameter";
|
||||
|
||||
@ -0,0 +1,53 @@
|
||||
---
|
||||
{
|
||||
"title": "SHA",
|
||||
"language": "en"
|
||||
}
|
||||
---
|
||||
|
||||
<!--
|
||||
Licensed to the Apache Software Foundation (ASF) under one
|
||||
or more contributor license agreements. See the NOTICE file
|
||||
distributed with this work for additional information
|
||||
regarding copyright ownership. The ASF licenses this file
|
||||
to you under the Apache License, Version 2.0 (the
|
||||
"License"); you may not use this file except in compliance
|
||||
with the License. You may obtain a copy of the License at
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
Unless required by applicable law or agreed to in writing,
|
||||
software distributed under the License is distributed on an
|
||||
"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
KIND, either express or implied. See the License for the
|
||||
specific language governing permissions and limitations
|
||||
under the License.
|
||||
-->
|
||||
|
||||
## SHA
|
||||
|
||||
### description
|
||||
|
||||
Use SHA1 to digest the message.
|
||||
|
||||
#### Syntax
|
||||
|
||||
`SHA(str)` or `SHA1(str)`
|
||||
|
||||
#### Arguments
|
||||
|
||||
- `str`: content to be encrypted
|
||||
|
||||
### example
|
||||
|
||||
```SQL
|
||||
mysql> select sha("123");
|
||||
+------------------------------------------+
|
||||
| sha1('123') |
|
||||
+------------------------------------------+
|
||||
| 40bd001563085fc35165329ea1ff5c5ecbdbbeef |
|
||||
+------------------------------------------+
|
||||
1 row in set (0.13 sec)
|
||||
```
|
||||
|
||||
### keywords
|
||||
|
||||
SHA,SHA1
|
||||
@ -0,0 +1,70 @@
|
||||
---
|
||||
{
|
||||
"title": "SHA2",
|
||||
"language": "en"
|
||||
}
|
||||
---
|
||||
|
||||
<!--
|
||||
Licensed to the Apache Software Foundation (ASF) under one
|
||||
or more contributor license agreements. See the NOTICE file
|
||||
distributed with this work for additional information
|
||||
regarding copyright ownership. The ASF licenses this file
|
||||
to you under the Apache License, Version 2.0 (the
|
||||
"License"); you may not use this file except in compliance
|
||||
with the License. You may obtain a copy of the License at
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
Unless required by applicable law or agreed to in writing,
|
||||
software distributed under the License is distributed on an
|
||||
"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
KIND, either express or implied. See the License for the
|
||||
specific language governing permissions and limitations
|
||||
under the License.
|
||||
-->
|
||||
|
||||
## SHA2
|
||||
|
||||
### description
|
||||
|
||||
Use SHA2 to digest the message.
|
||||
|
||||
#### Syntax
|
||||
|
||||
`SHA2(str, digest_length)`
|
||||
|
||||
#### Arguments
|
||||
|
||||
- `str`: content to be encrypted
|
||||
- `digest_length`: the length of the digest
|
||||
|
||||
### example
|
||||
|
||||
```SQL
|
||||
mysql> select sha2('abc', 224);
|
||||
+----------------------------------------------------------+
|
||||
| sha2('abc', 224) |
|
||||
+----------------------------------------------------------+
|
||||
| 23097d223405d8228642a477bda255b32aadbce4bda0b3f7e36c9da7 |
|
||||
+----------------------------------------------------------+
|
||||
1 row in set (0.13 sec)
|
||||
|
||||
mysql> select sha2('abc', 384);
|
||||
+--------------------------------------------------------------------------------------------------+
|
||||
| sha2('abc', 384) |
|
||||
+--------------------------------------------------------------------------------------------------+
|
||||
| cb00753f45a35e8bb5a03d699ac65007272c32ab0eded1631a8b605a43ff5bed8086072ba1e7cc2358baeca134c825a7 |
|
||||
+--------------------------------------------------------------------------------------------------+
|
||||
1 row in set (0.13 sec)
|
||||
|
||||
mysql> select sha2(NULL, 512);
|
||||
+-----------------+
|
||||
| sha2(NULL, 512) |
|
||||
+-----------------+
|
||||
| NULL |
|
||||
+-----------------+
|
||||
1 row in set (0.09 sec)
|
||||
```
|
||||
|
||||
### keywords
|
||||
|
||||
SHA2
|
||||
@ -713,7 +713,9 @@
|
||||
"sql-manual/sql-functions/encrypt-digest-functions/md5sum",
|
||||
"sql-manual/sql-functions/encrypt-digest-functions/sm4",
|
||||
"sql-manual/sql-functions/encrypt-digest-functions/sm3",
|
||||
"sql-manual/sql-functions/encrypt-digest-functions/sm3sum"
|
||||
"sql-manual/sql-functions/encrypt-digest-functions/sm3sum",
|
||||
"sql-manual/sql-functions/encrypt-digest-functions/sha",
|
||||
"sql-manual/sql-functions/encrypt-digest-functions/sha2"
|
||||
]
|
||||
},
|
||||
{
|
||||
|
||||
@ -0,0 +1,54 @@
|
||||
---
|
||||
{
|
||||
"title": "SHA",
|
||||
"language": "zh-CN"
|
||||
}
|
||||
---
|
||||
|
||||
<!--
|
||||
Licensed to the Apache Software Foundation (ASF) under one
|
||||
or more contributor license agreements. See the NOTICE file
|
||||
distributed with this work for additional information
|
||||
regarding copyright ownership. The ASF licenses this file
|
||||
to you under the Apache License, Version 2.0 (the
|
||||
"License"); you may not use this file except in compliance
|
||||
with the License. You may obtain a copy of the License at
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
Unless required by applicable law or agreed to in writing,
|
||||
software distributed under the License is distributed on an
|
||||
"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
KIND, either express or implied. See the License for the
|
||||
specific language governing permissions and limitations
|
||||
under the License.
|
||||
-->
|
||||
|
||||
## SHA
|
||||
|
||||
### description
|
||||
|
||||
使用SHA1算法对信息进行摘要处理。
|
||||
|
||||
#### Syntax
|
||||
|
||||
`SHA(str)` 或 `SHA1(str)`
|
||||
|
||||
#### Arguments
|
||||
|
||||
- `str`: 待加密的内容
|
||||
|
||||
### example
|
||||
|
||||
```SQL
|
||||
mysql> select sha("123");
|
||||
+------------------------------------------+
|
||||
| sha1('123') |
|
||||
+------------------------------------------+
|
||||
| 40bd001563085fc35165329ea1ff5c5ecbdbbeef |
|
||||
+------------------------------------------+
|
||||
1 row in set (0.13 sec)
|
||||
```
|
||||
|
||||
### keywords
|
||||
|
||||
SHA,SHA1
|
||||
|
||||
@ -0,0 +1,70 @@
|
||||
---
|
||||
{
|
||||
"title": "SHA2",
|
||||
"language": "zh-CN"
|
||||
}
|
||||
---
|
||||
|
||||
<!--
|
||||
Licensed to the Apache Software Foundation (ASF) under one
|
||||
or more contributor license agreements. See the NOTICE file
|
||||
distributed with this work for additional information
|
||||
regarding copyright ownership. The ASF licenses this file
|
||||
to you under the Apache License, Version 2.0 (the
|
||||
"License"); you may not use this file except in compliance
|
||||
with the License. You may obtain a copy of the License at
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
Unless required by applicable law or agreed to in writing,
|
||||
software distributed under the License is distributed on an
|
||||
"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
KIND, either express or implied. See the License for the
|
||||
specific language governing permissions and limitations
|
||||
under the License.
|
||||
-->
|
||||
|
||||
## SHA2
|
||||
|
||||
### description
|
||||
|
||||
使用SHA2对信息进行摘要处理。
|
||||
|
||||
#### Syntax
|
||||
|
||||
`SHA2(str, digest_length)`
|
||||
|
||||
#### Arguments
|
||||
|
||||
- `str`: 待加密的内容
|
||||
- `digest_length`: 摘要长度
|
||||
|
||||
### example
|
||||
|
||||
```SQL
|
||||
mysql> select sha2('abc', 224);
|
||||
+----------------------------------------------------------+
|
||||
| sha2('abc', 224) |
|
||||
+----------------------------------------------------------+
|
||||
| 23097d223405d8228642a477bda255b32aadbce4bda0b3f7e36c9da7 |
|
||||
+----------------------------------------------------------+
|
||||
1 row in set (0.13 sec)
|
||||
|
||||
mysql> select sha2('abc', 384);
|
||||
+--------------------------------------------------------------------------------------------------+
|
||||
| sha2('abc', 384) |
|
||||
+--------------------------------------------------------------------------------------------------+
|
||||
| cb00753f45a35e8bb5a03d699ac65007272c32ab0eded1631a8b605a43ff5bed8086072ba1e7cc2358baeca134c825a7 |
|
||||
+--------------------------------------------------------------------------------------------------+
|
||||
1 row in set (0.13 sec)
|
||||
|
||||
mysql> select sha2(NULL, 512);
|
||||
+-----------------+
|
||||
| sha2(NULL, 512) |
|
||||
+-----------------+
|
||||
| NULL |
|
||||
+-----------------+
|
||||
1 row in set (0.09 sec)
|
||||
```
|
||||
|
||||
### keywords
|
||||
|
||||
SHA2
|
||||
@ -1704,6 +1704,19 @@ public class FunctionCallExpr extends Expr {
|
||||
}
|
||||
}
|
||||
|
||||
if (fn.getFunctionName().getFunction().equals("sha2")) {
|
||||
if ((children.size() != 2) || (getChild(1).isConstant() == false)
|
||||
|| !(getChild(1) instanceof IntLiteral)) {
|
||||
throw new AnalysisException(
|
||||
fnName.getFunction() + " needs two params, and the second is must be a integer constant: "
|
||||
+ this.toSql());
|
||||
}
|
||||
final Integer constParam = (int) ((IntLiteral) getChild(1)).getValue();
|
||||
if (!Lists.newArrayList(224, 256, 384, 512).contains(constParam)) {
|
||||
throw new AnalysisException("sha2 functions only support digest length of 224/256/384/512");
|
||||
}
|
||||
}
|
||||
|
||||
if (isAggregateFunction()) {
|
||||
final String functionName = fnName.getFunction();
|
||||
// subexprs must not contain aggregates
|
||||
|
||||
@ -294,6 +294,8 @@ import org.apache.doris.nereids.trees.expressions.functions.scalar.SecondTimesta
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.SecondsAdd;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.SecondsDiff;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.SecondsSub;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.Sha1;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.Sha2;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.Sign;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.Sin;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.Sleep;
|
||||
@ -690,6 +692,8 @@ public class BuiltinScalarFunctions implements FunctionHelper {
|
||||
scalar(SecondTimestamp.class, "second_timestamp"),
|
||||
scalar(MilliSecondTimestamp.class, "millisecond_timestamp"),
|
||||
scalar(MicroSecondTimestamp.class, "microsecond_timestamp"),
|
||||
scalar(Sha1.class, "sha1", "sha"),
|
||||
scalar(Sha2.class, "sha2"),
|
||||
scalar(Sign.class, "sign"),
|
||||
scalar(Sin.class, "sin"),
|
||||
scalar(Sleep.class, "sleep"),
|
||||
|
||||
@ -0,0 +1,68 @@
|
||||
// Licensed to the Apache Software Foundation (ASF) under one
|
||||
// or more contributor license agreements. See the NOTICE file
|
||||
// distributed with this work for additional information
|
||||
// regarding copyright ownership. The ASF licenses this file
|
||||
// to you under the Apache License, Version 2.0 (the
|
||||
// "License"); you may not use this file except in compliance
|
||||
// with the License. You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing,
|
||||
// software distributed under the License is distributed on an
|
||||
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
// KIND, either express or implied. See the License for the
|
||||
// specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
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.PropagateNullable;
|
||||
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
|
||||
import org.apache.doris.nereids.types.StringType;
|
||||
import org.apache.doris.nereids.types.VarcharType;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
import com.google.common.collect.ImmutableList;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* ScalarFunction 'sha1'. This class is not generated by GenerateFunction.
|
||||
*/
|
||||
public class Sha1 extends ScalarFunction
|
||||
implements ExplicitlyCastableSignature, PropagateNullable {
|
||||
|
||||
public static final List<FunctionSignature> SIGNATURES = ImmutableList.of(
|
||||
FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).args(VarcharType.SYSTEM_DEFAULT),
|
||||
FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).args(StringType.INSTANCE));
|
||||
|
||||
/**
|
||||
* constructor with 1 arguments.
|
||||
*/
|
||||
public Sha1(Expression arg0) {
|
||||
super("sha1", arg0);
|
||||
}
|
||||
|
||||
/**
|
||||
* withChildren.
|
||||
*/
|
||||
@Override
|
||||
public Sha1 withChildren(List<Expression> children) {
|
||||
Preconditions.checkArgument(children.size() == 1);
|
||||
return new Sha1(children.get(0));
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<FunctionSignature> getSignatures() {
|
||||
return SIGNATURES;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <R, C> R accept(ExpressionVisitor<R, C> visitor, C context) {
|
||||
return visitor.visitSha1(this, context);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,69 @@
|
||||
// Licensed to the Apache Software Foundation (ASF) under one
|
||||
// or more contributor license agreements. See the NOTICE file
|
||||
// distributed with this work for additional information
|
||||
// regarding copyright ownership. The ASF licenses this file
|
||||
// to you under the Apache License, Version 2.0 (the
|
||||
// "License"); you may not use this file except in compliance
|
||||
// with the License. You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing,
|
||||
// software distributed under the License is distributed on an
|
||||
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
// KIND, either express or implied. See the License for the
|
||||
// specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
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.PropagateNullable;
|
||||
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
|
||||
import org.apache.doris.nereids.types.IntegerType;
|
||||
import org.apache.doris.nereids.types.StringType;
|
||||
import org.apache.doris.nereids.types.VarcharType;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
import com.google.common.collect.ImmutableList;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* ScalarFunction 'sha2'. This class is not generated by GenerateFunction.
|
||||
*/
|
||||
public class Sha2 extends ScalarFunction
|
||||
implements ExplicitlyCastableSignature, PropagateNullable {
|
||||
|
||||
public static final List<FunctionSignature> SIGNATURES = ImmutableList.of(
|
||||
FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).args(VarcharType.SYSTEM_DEFAULT, IntegerType.INSTANCE),
|
||||
FunctionSignature.ret(VarcharType.SYSTEM_DEFAULT).args(StringType.INSTANCE, IntegerType.INSTANCE));
|
||||
|
||||
/**
|
||||
* constructor with 2 arguments.
|
||||
*/
|
||||
public Sha2(Expression arg0, Expression arg1) {
|
||||
super("sha2", arg0, arg1);
|
||||
}
|
||||
|
||||
/**
|
||||
* withChildren.
|
||||
*/
|
||||
@Override
|
||||
public Sha2 withChildren(List<Expression> children) {
|
||||
Preconditions.checkArgument(children.size() == 2);
|
||||
return new Sha2(children.get(0), children.get(1));
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<FunctionSignature> getSignatures() {
|
||||
return SIGNATURES;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <R, C> R accept(ExpressionVisitor<R, C> visitor, C context) {
|
||||
return visitor.visitSha2(this, context);
|
||||
}
|
||||
}
|
||||
@ -290,6 +290,8 @@ import org.apache.doris.nereids.trees.expressions.functions.scalar.SecondFloor;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.SecondsAdd;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.SecondsDiff;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.SecondsSub;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.Sha1;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.Sha2;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.Sign;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.Sin;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.scalar.Sleep;
|
||||
@ -1434,6 +1436,14 @@ public interface ScalarFunctionVisitor<R, C> {
|
||||
return visitScalarFunction(secondsDiff, context);
|
||||
}
|
||||
|
||||
default R visitSha1(Sha1 sha1, C context) {
|
||||
return visitScalarFunction(sha1, context);
|
||||
}
|
||||
|
||||
default R visitSha2(Sha2 sha2, C context) {
|
||||
return visitScalarFunction(sha2, context);
|
||||
}
|
||||
|
||||
default R visitMilliSecondsDiff(MilliSecondsDiff milliSecondsDiff, C context) {
|
||||
return visitScalarFunction(milliSecondsDiff, context);
|
||||
}
|
||||
|
||||
@ -1920,6 +1920,13 @@ visible_functions = {
|
||||
[['sm3sum'], 'VARCHAR', ['VARCHAR', '...'], ''],
|
||||
[['sm3'], 'VARCHAR', ['STRING'], ''],
|
||||
[['sm3sum'], 'VARCHAR', ['STRING', '...'], ''],
|
||||
|
||||
[['sha'], 'VARCHAR', ['VARCHAR'], ''],
|
||||
[['sha'], 'VARCHAR', ['STRING'], ''],
|
||||
[['sha1'], 'VARCHAR', ['VARCHAR'], ''],
|
||||
[['sha1'], 'VARCHAR', ['STRING'], ''],
|
||||
[['sha2'], 'VARCHAR', ['VARCHAR', 'INT'], ''],
|
||||
[['sha2'], 'VARCHAR', ['STRING', 'INT'], ''],
|
||||
],
|
||||
|
||||
# geo functions
|
||||
|
||||
@ -0,0 +1,39 @@
|
||||
-- This file is automatically generated. You should know what you did if you want to edit this
|
||||
-- !md5 --
|
||||
68934a3e9455fa72420237eb05902327
|
||||
68934a3e9455fa72420237eb05902327
|
||||
b326b5062b2f0e69046810717534cb09
|
||||
|
||||
-- !sha1_1 --
|
||||
40bd001563085fc35165329ea1ff5c5ecbdbbeef
|
||||
|
||||
-- !sha1_2 --
|
||||
01b61f61abb0108346025d913eba241ec600da51 01b61f61abb0108346025d913eba241ec600da51
|
||||
e20afd4c8d2f7966348494bc4a8b3ba2406479c3 e20afd4c8d2f7966348494bc4a8b3ba2406479c3
|
||||
ecfb6e9d7b67d81c6f4a11c6df1bd5cc7d38d21e ecfb6e9d7b67d81c6f4a11c6df1bd5cc7d38d21e
|
||||
|
||||
-- !sha1_3 --
|
||||
da39a3ee5e6b4b0d3255bfef95601890afd80709
|
||||
|
||||
-- !sha1_4 --
|
||||
\N
|
||||
|
||||
-- !sha2_1 --
|
||||
be504c074c5a9e0a461d8dd6e1160ac8343e5d70bbd05082868e09edc9b17c50
|
||||
86aa74b42da827c630e4a3efaeb660823af67e540828576e8413e31ac95fd494
|
||||
86d137f8ee3da44ded006c55a3b6f3460121711df8a789bf146a6d2ce3995311
|
||||
|
||||
-- !sha2_2 --
|
||||
10a699b0850fad1c219f933f821e472630eac91cc34b2e8d254b2326ab8ca025ea9fdaa1db5e7b4c1d6b84a525524f8f3100e9847e1504b199728ddf0ce3e134
|
||||
a0296b74d1f31c0ce956f793efeb003c5e987b8f4546c8a02dcadf19073ff717d86fca57bdd0f532067b4757a7d0b924bcf4c471c05f671d775bac4f00638152
|
||||
6f2c68ec336dab0e4eb4746053bd4040b181cf75a4189dff729c6ac9a8e5062440bf5b6dc0f8ae3ed8859e1aa2a55626b1ae36191c34d41362766bcac9bc2ace
|
||||
|
||||
-- !sha2_3 --
|
||||
23097d223405d8228642a477bda255b32aadbce4bda0b3f7e36c9da7
|
||||
|
||||
-- !sha2_4 --
|
||||
cb00753f45a35e8bb5a03d699ac65007272c32ab0eded1631a8b605a43ff5bed8086072ba1e7cc2358baeca134c825a7
|
||||
|
||||
-- !sha2_5 --
|
||||
\N
|
||||
|
||||
@ -1,6 +0,0 @@
|
||||
-- This file is automatically generated. You should know what you did if you want to edit this
|
||||
-- !select --
|
||||
68934a3e9455fa72420237eb05902327
|
||||
68934a3e9455fa72420237eb05902327
|
||||
b326b5062b2f0e69046810717534cb09
|
||||
|
||||
@ -15,6 +15,21 @@
|
||||
// specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
suite("test_md5") {
|
||||
qt_select "select md5(k6) from test_query_db.test order by k6"
|
||||
suite("test_digest") {
|
||||
qt_md5 "select md5(k6) from test_query_db.test order by k6"
|
||||
qt_sha1_1 "select sha1(\"123\")"
|
||||
qt_sha1_2 "select sha(k7), sha1(k7) from test_query_db.test order by k7"
|
||||
qt_sha1_3 "select sha1(\"\")"
|
||||
qt_sha1_4 "select sha1(NULL)"
|
||||
qt_sha2_1 "select sha2(k7, 256) from test_query_db.test order by k7"
|
||||
qt_sha2_2 "select sha2(k7, 512) from test_query_db.test order by k7"
|
||||
qt_sha2_3 "select sha2('abc', 224)"
|
||||
qt_sha2_4 "select sha2('abc', 384)"
|
||||
qt_sha2_5 "select sha2(NULL, 384)"
|
||||
|
||||
try {
|
||||
result = sql """ select sha2("123", 255) """
|
||||
} catch (Exception e) {
|
||||
assertTrue(e.getMessage().contains("only support 224/256/384/512"))
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user