You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@doris.apache.org by zy...@apache.org on 2023/06/28 14:51:24 UTC
[doris] branch master updated: [fix](jdbc) Handling Zero DateTime Values in Non-nullable Columns for JDBC Catalog Reading MySQL (#21296)
This is an automated email from the ASF dual-hosted git repository.
zykkk 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 449c8d4568 [fix](jdbc) Handling Zero DateTime Values in Non-nullable Columns for JDBC Catalog Reading MySQL (#21296)
449c8d4568 is described below
commit 449c8d4568cfb9d0bd5e787a0c16e31f0d98425b
Author: zy-kkk <zh...@gmail.com>
AuthorDate: Wed Jun 28 22:51:17 2023 +0800
[fix](jdbc) Handling Zero DateTime Values in Non-nullable Columns for JDBC Catalog Reading MySQL (#21296)
---
.../docker-compose/mysql/init/03-create-table.sql | 22 +++++++++++++---------
.../docker-compose/mysql/init/04-insert.sql | 3 +++
docs/en/docs/lakehouse/multi-catalog/jdbc.md | 14 +++++++++++++-
docs/zh-CN/docs/lakehouse/multi-catalog/jdbc.md | 14 +++++++++++++-
.../doris/external/jdbc/JdbcMySQLClient.java | 12 ++++++++++++
.../jdbc_catalog_p0/test_mysql_jdbc_catalog.out | 4 ++++
.../jdbc_catalog_p0/test_mysql_jdbc_catalog.groovy | 4 +++-
7 files changed, 61 insertions(+), 12 deletions(-)
diff --git a/docker/thirdparties/docker-compose/mysql/init/03-create-table.sql b/docker/thirdparties/docker-compose/mysql/init/03-create-table.sql
index 9845db17bf..f1c45b7b1e 100644
--- a/docker/thirdparties/docker-compose/mysql/init/03-create-table.sql
+++ b/docker/thirdparties/docker-compose/mysql/init/03-create-table.sql
@@ -291,12 +291,16 @@ CREATE TABLE `doris_test`.`auto_default_t` (
PRIMARY KEY (`id`)
) engine=innodb charset=utf8;
-create table doris_test.dt (
- `timestamp0` timestamp(0),
- `timestamp1` timestamp(1),
- `timestamp2` timestamp(2),
- `timestamp3` timestamp(3),
- `timestamp4` timestamp(4),
- `timestamp5` timestamp(5),
- `timestamp6` timestamp(6)
-) engine=innodb charset=utf8;
\ No newline at end of file
+CREATE TABLE doris_test.dt (
+ `timestamp0` timestamp(0) DEFAULT CURRENT_TIMESTAMP(0),
+ `timestamp1` timestamp(1) DEFAULT CURRENT_TIMESTAMP(1),
+ `timestamp2` timestamp(2) DEFAULT CURRENT_TIMESTAMP(2),
+ `timestamp3` timestamp(3) DEFAULT CURRENT_TIMESTAMP(3),
+ `timestamp4` timestamp(4) DEFAULT CURRENT_TIMESTAMP(4),
+ `timestamp5` timestamp(5) DEFAULT CURRENT_TIMESTAMP(5),
+ `timestamp6` timestamp(6) DEFAULT CURRENT_TIMESTAMP(6)
+) ENGINE=INNODB CHARSET=utf8;
+
+CREATE TABLE doris_test.dt_null (
+ `dt` datetime NOT NULL
+) ENGINE=INNODB CHARSET=utf8;
\ No newline at end of file
diff --git a/docker/thirdparties/docker-compose/mysql/init/04-insert.sql b/docker/thirdparties/docker-compose/mysql/init/04-insert.sql
index c164bb3b82..fbbe2221bb 100644
--- a/docker/thirdparties/docker-compose/mysql/init/04-insert.sql
+++ b/docker/thirdparties/docker-compose/mysql/init/04-insert.sql
@@ -1143,3 +1143,6 @@ INSERT INTO doris_test.dt (`timestamp0`, `timestamp1`, `timestamp2`, `timestamp3
VALUES ('2023-06-17 10:00:00', '2023-06-17 10:00:01.1', '2023-06-17 10:00:02.22', '2023-06-17 10:00:03.333',
'2023-06-17 10:00:04.4444', '2023-06-17 10:00:05.55555', '2023-06-17 10:00:06.666666');
+SET SESSION sql_mode=(SELECT REPLACE(@@sql_mode,'STRICT_TRANS_TABLES',''));
+INSERT INTO doris_test.dt_null
+VALUES ('2023-06-17 10:00:00'),('0000-00-00 00:00:00');
diff --git a/docs/en/docs/lakehouse/multi-catalog/jdbc.md b/docs/en/docs/lakehouse/multi-catalog/jdbc.md
index 9e1d804928..7be1ae4557 100644
--- a/docs/en/docs/lakehouse/multi-catalog/jdbc.md
+++ b/docs/en/docs/lakehouse/multi-catalog/jdbc.md
@@ -675,4 +675,16 @@ When Doris connects to OceanBase, it will automatically recognize that OceanBase
unable to find valid certification path to requested target". ClientConnectionId:a92f3817-e8e6-4311-bc21-7c66
```
- In the create Catalog `jdbc_url` the JDBC connection string finally increase `encrypt=false`, such as `"jdbc_url" = "jdbc:sqlserver://127.0.0.1:1433;DataBaseName=doris_test;encrypt=false"`
\ No newline at end of file
+ In the create Catalog `jdbc_url` the JDBC connection string finally increase `encrypt=false`, such as `"jdbc_url" = "jdbc:sqlserver://127.0.0.1:1433;DataBaseName=doris_test;encrypt=false"`
+
+11. Error encountered when reading MySQL datetime type
+
+ ```
+ ERROR 1105 (HY000): errCode = 2, detailMessage = (10.16.10.6)[INTERNAL_ERROR]UdfRuntimeException: get next block failed:
+ CAUSED BY: SQLException: Zero date value prohibited
+ CAUSED BY: DataReadException: Zero date value prohibited
+ ```
+
+ This happens because JDBC can't handle the datetime format 0000-00-00 00:00:00.
+ To address this, append zeroDateTimeBehavior=convertToNull to the jdbc_url when creating the Catalog, e.g., "jdbc_url" = "jdbc:mysql://127.0.0.1:3306/test?zeroDateTimeBehavior=convertToNull".
+ In this case, JDBC will convert 0000-00-00 00:00:00 to null, and then Doris will handle the DateTime column as a nullable type, allowing for successful reading.
\ No newline at end of file
diff --git a/docs/zh-CN/docs/lakehouse/multi-catalog/jdbc.md b/docs/zh-CN/docs/lakehouse/multi-catalog/jdbc.md
index b02180ce82..e706bf3521 100644
--- a/docs/zh-CN/docs/lakehouse/multi-catalog/jdbc.md
+++ b/docs/zh-CN/docs/lakehouse/multi-catalog/jdbc.md
@@ -670,4 +670,16 @@ CREATE CATALOG jdbc_oceanbase PROPERTIES (
unable to find valid certification path to requested target". ClientConnectionId:a92f3817-e8e6-4311-bc21-7c66
```
- 可在创建 Catalog 的 `jdbc_url` 把JDBC连接串最后增加 `encrypt=false` ,如 `"jdbc_url" = "jdbc:sqlserver://127.0.0.1:1433;DataBaseName=doris_test;encrypt=false"`
\ No newline at end of file
+ 可在创建 Catalog 的 `jdbc_url` 把JDBC连接串最后增加 `encrypt=false` ,如 `"jdbc_url" = "jdbc:sqlserver://127.0.0.1:1433;DataBaseName=doris_test;encrypt=false"`
+
+11. 读取 MySQL datetime 类型出现异常
+
+ ```
+ ERROR 1105 (HY000): errCode = 2, detailMessage = (10.16.10.6)[INTERNAL_ERROR]UdfRuntimeException: get next block failed:
+ CAUSED BY: SQLException: Zero date value prohibited
+ CAUSED BY: DataReadException: Zero date value prohibited
+ ```
+
+ 这是因为 JDBC 并不能处理 0000-00-00 00:00:00 这种时间格式,
+ 需要在创建 Catalog 的 `jdbc_url` 把JDBC连接串最后增加 `zeroDateTimeBehavior=convertToNull` ,如 `"jdbc_url" = "jdbc:mysql://127.0.0.1:3306/test?zeroDateTimeBehavior=convertToNull"`
+ 这种情况下,JDBC 会把 0000-00-00 00:00:00 转换成 null,然后 Doris 会把 DateTime 类型的列按照可空类型处理,这样就可以正常读取了。
\ No newline at end of file
diff --git a/fe/fe-core/src/main/java/org/apache/doris/external/jdbc/JdbcMySQLClient.java b/fe/fe-core/src/main/java/org/apache/doris/external/jdbc/JdbcMySQLClient.java
index c5ceefb89d..a6c0ce29a2 100644
--- a/fe/fe-core/src/main/java/org/apache/doris/external/jdbc/JdbcMySQLClient.java
+++ b/fe/fe-core/src/main/java/org/apache/doris/external/jdbc/JdbcMySQLClient.java
@@ -36,8 +36,12 @@ import java.util.Map;
import java.util.function.Consumer;
public class JdbcMySQLClient extends JdbcClient {
+
+ private static boolean convertDateToNull = false;
+
protected JdbcMySQLClient(JdbcClientConfig jdbcClientConfig) {
super(jdbcClientConfig);
+ convertDateToNull = isConvertDatetimeToNull(jdbcClientConfig);
}
@Override
@@ -281,6 +285,9 @@ public class JdbcMySQLClient extends JdbcClient {
if (scale > 6) {
scale = 6;
}
+ if (convertDateToNull) {
+ fieldSchema.setAllowNull(true);
+ }
return ScalarType.createDatetimeV2Type(scale);
}
case "FLOAT":
@@ -331,4 +338,9 @@ public class JdbcMySQLClient extends JdbcClient {
return Type.UNSUPPORTED;
}
}
+
+ private boolean isConvertDatetimeToNull(JdbcClientConfig jdbcClientConfig) {
+ // Check if the JDBC URL contains "zeroDateTimeBehavior=convertToNull".
+ return jdbcClientConfig.getJdbcUrl().contains("zeroDateTimeBehavior=convertToNull");
+ }
}
diff --git a/regression-test/data/jdbc_catalog_p0/test_mysql_jdbc_catalog.out b/regression-test/data/jdbc_catalog_p0/test_mysql_jdbc_catalog.out
index e1a5431b00..458b5fa14a 100644
--- a/regression-test/data/jdbc_catalog_p0/test_mysql_jdbc_catalog.out
+++ b/regression-test/data/jdbc_catalog_p0/test_mysql_jdbc_catalog.out
@@ -252,6 +252,10 @@ VIEW_TABLE_USAGE
-- !dt --
2023-06-17T10:00 2023-06-17T10:00:01.100 2023-06-17T10:00:02.220 2023-06-17T10:00:03.333 2023-06-17T10:00:04.444400 2023-06-17T10:00:05.555550 2023-06-17T10:00:06.666666
+-- !dt_null --
+\N
+2023-06-17T10:00
+
-- !test_insert1 --
doris1 18
diff --git a/regression-test/suites/jdbc_catalog_p0/test_mysql_jdbc_catalog.groovy b/regression-test/suites/jdbc_catalog_p0/test_mysql_jdbc_catalog.groovy
index 81373b502d..5551217c98 100644
--- a/regression-test/suites/jdbc_catalog_p0/test_mysql_jdbc_catalog.groovy
+++ b/regression-test/suites/jdbc_catalog_p0/test_mysql_jdbc_catalog.groovy
@@ -50,6 +50,7 @@ suite("test_mysql_jdbc_catalog", "p0") {
String test_insert2 = "test_insert2";
String auto_default_t = "auto_default_t";
String dt = "dt";
+ String dt_null = "dt_null";
sql """drop catalog if exists ${catalog_name} """
@@ -57,7 +58,7 @@ suite("test_mysql_jdbc_catalog", "p0") {
"type"="jdbc",
"user"="root",
"password"="123456",
- "jdbc_url" = "jdbc:mysql://127.0.0.1:${mysql_port}/doris_test?useSSL=false",
+ "jdbc_url" = "jdbc:mysql://127.0.0.1:${mysql_port}/doris_test?useSSL=false&zeroDateTimeBehavior=convertToNull",
"driver_url" = "https://doris-community-test-1308700295.cos.ap-hongkong.myqcloud.com/jdbc_driver/mysql-connector-java-8.0.25.jar",
"driver_class" = "com.mysql.cj.jdbc.Driver"
);"""
@@ -103,6 +104,7 @@ suite("test_mysql_jdbc_catalog", "p0") {
order_qt_information_schema """ show tables from information_schema; """
order_qt_auto_default_t """insert into ${auto_default_t}(name) values('a'); """
order_qt_dt """select * from ${dt}; """
+ order_qt_dt_null """select * from ${dt_null} order by 1; """
// test insert
String uuid1 = UUID.randomUUID().toString();
---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@doris.apache.org
For additional commands, e-mail: commits-help@doris.apache.org