认证培训专区
学习笔记
文章

GBase 8a MPP LOAD DATA 踩坑实录:反斜杠转义引发的Out of range value

发表于2026-09-04 12:52:57239次浏览2个评论

一、问题现象

使用 LOAD DATA 导入包含时间字段的文本文件时,出现Out of range value现象:

  • 任务返回 Loaded 0 records, Skipped 10 records,全部数据被跳过,0 行入库
  • 查看加载追踪日志(.trc),报错 Out of range value
  • 但检查数据内容,时间格式看起来完全正常,字段类型也匹配

最初被日志报错误导,以为是数据超过数据类型边界,最终定位根因是:数据文件中携带反斜杠转义字符,被LOAD解析器处理后破坏了原始时间字符串。

二、测试环境

2.1 业务表建表语句

CREATE TABLE t_loaddata (
    i INT,
    vc VARCHAR(10),
    dt DATETIME DEFAULT '2000-01-01 00:00:01',
    dt1 DATETIME DEFAULT '2000-01-01 00:00:01'
);

2.2 GBase 8a 官方日期时间类型范围

先明确官方定义的类型范围,避免不必要的误判:

类型 最小值 最大值 格式
DATE 0001-01-01 9999-12-31 YYYY-MM-DD
DATETIME 0001-01-01 00:00:00.000000 9999-12-31 23:59:59.999999 YYYY-MM-DD HH:MI:SS.ffffff
TIME -838:59:59 838:59:59 HHH:MI:SS
TIMESTAMP 1970-01-01 08:00:01 2038-01-19 03:14:07 YYYY-MM-DD HH:MI:SS

注意:TIMESTAMP 受 32 位 Unix 时间戳约束存在硬上限,DATETIME 和 DATE 官方支持到 9999 年。

三、问题排查

3.1 出问题的数据文件

数据文件中第四列时间字段书写了 01\:01\:01,反斜杠会原样写入文本文件。

cat >> testdata.txt <<EOF
31589,E,02:02:02 2094-12-13,2082-12-24 01\:01\:01
16993,jcWaz,02:02:02 2060-10-22,2037-11-17 01\:01\:01
7584,jubNKAmT,02:02:02 2058-12-24,2066-11-26 01\:01\:01
8698,iOStkY,02:02:02 2024-11-17,2064-10-25 01\:01\:01
23256,itWsHqL,02:02:02 2069-10-24,2021-11-19 01\:01\:01
21932,GelDJbuE,02:02:02 2017-11-26,2075-11-19 01\:01\:01
4859,Gl,02:02:02 2040-10-16,2051-10-25 01\:01\:01
11751,InTUcdIM,02:02:02 2048-12-23,2099-10-26 01\:01\:01
8487,JZ,02:02:02 2026-12-13,2084-11-15 01\:01\:01
3693,lEKyI,02:02:02 2063-10-21,2026-11-20 01\:01\:01
EOF

3.2 执行 LOAD 语句

LOAD DATA 
    INFILE 'file://*.*.*.21/home/gbase/testdata1.txt' 
    INTO TABLE testdb.t_loaddata 
    fields terminated by ',' 
    TABLE_FIELDS 'i, vc, dt date "%H:%i:%s %Y-%m-%d", dt1 date "%Y-%m-%d %H:%i:%s"'

-- 执行结果:
Query OK, 0 rows affected (Elapsed: 00:00:00.99)
Task 3081 finished, Loaded 0 records, Skipped 10 records```

3.3 查看加载日志定位

GBase 8a LOAD 任务日志默认路径,先查询日志根目录:

gbase> show variables like '%loader_logs%';
+---------------------------+---------------------------------------------------------------+
| Variable_name             | Value                                                         |
+---------------------------+---------------------------------------------------------------+
| gbase_loader_logs_collect | ON                                                            |
| gbase_loader_logs_dir     | /data/gbase/*.*.*.21/gcluster/log/gcluster/loader_logs/ |
+---------------------------+---------------------------------------------------------------+

装载任务日志目录:/data/gbase/*.*.*.21/gcluster/log/gcluster/loader_logs/任务号/

文件 作用
*.trc 排错优先查看,记录每一行跳过的字段、偏移、真实原因
*.err 被跳过的原始脏数据行
*_loader_result.log 任务统计汇总

查看 .trc 日志: 日志显示第4列(dt1)报 Out of range value,但反复核对数据,时间格式和内容看起来都没问题。

cat /data/gbase/***.***.***.21/gcluster/log/gcluster/loader_logs/3081/3081_testdb_t_loaddata_n1_172.168.100.21_20260904112927.trc
file_name    |   file_offset    |   record_len   |   column    |    reason
/home/gbase/testdata.txt|0|50|4|Out of range value
… …
/home/gbase/testdata.txt|484|53|4|Out of range value

3.4 关键发现:反斜杠转义字符

根因分析:

数据文件字段内存在反斜杠\,破坏原始时间字符串。

日志的 Out of range value 是解析失败后的报错,并不是数据本身超出数据类型存储范围。

四、移除反斜杠后正常装载

4.1 生成干净的测试文件

预处理源文件,清除多余反斜杠

sed -i 's#\\:#:#g' testdata.txt

cat >> testdata.txt <<EOF
31589,E,02:02:02 2094-12-13,2082-12-24 01:01:01
16993,jcWaz,02:02:02 2060-10-22,2037-11-17 01:01:01
7584,jubNKAmT,02:02:02 2058-12-24,2066-11-26 01:01:01
8698,iOStkY,02:02:02 2024-11-17,2064-10-25 01:01:01
23256,itWsHqL,02:02:02 2069-10-24,2021-11-19 01:01:01
21932,GelDJbuE,02:02:02 2017-11-26,2075-11-19 01:01:01
4859,Gl,02:02:02 2040-10-16,2051-10-25 01:01:01
11751,InTUcdIM,02:02:02 2048-12-23,2099-10-26 01:01:01
8487,JZ,02:02:02 2026-12-13,2084-11-15 01:01:01
3693,lEKyI,02:02:02 2063-10-21,2026-11-20 01:01:01
EOF

4.2 执行相同的 LOAD 语句

LOAD DATA 
    INFILE 'file://*.*.*.21/home/gbase/testdata1.txt' 
    INTO TABLE testdb.t_loaddata 
    fields terminated by ',' 
    TABLE_FIELDS 'i, vc, dt date "%H:%i:%s %Y-%m-%d", dt1 date "%Y-%m-%d %H:%i:%s"'
;

-- 执行结果
Query OK, 10 rows affected (Elapsed: 00:00:00.38)
Task 3092 finished, Loaded 10 records, Skipped 0 records

-- 查询验证

SELECT * FROM testdb.t_loaddata;
+-------+----------+---------------------+---------------------+
| i     | vc       | dt                  | dt1                 |
+-------+----------+---------------------+---------------------+
|  7584 | jubNKAmT | 2058-12-24 02:02:02 | 2066-11-26 01:01:01 |
|  8487 | JZ       | 2026-12-13 02:02:02 | 2084-11-15 01:01:01 |
| 16993 | jcWaz    | 2060-10-22 02:02:02 | 2037-11-17 01:01:01 |
| 11751 | InTUcdIM | 2048-12-23 02:02:02 | 2099-10-26 01:01:01 |
| 23256 | itWsHqL  | 2069-10-24 02:02:02 | 2021-11-19 01:01:01 |
|  8698 | iOStkY   | 2024-11-17 02:02:02 | 2064-10-25 01:01:01 |
|  3693 | lEKyI    | 2063-10-21 02:02:02 | 2026-11-20 01:01:01 |
| 31589 | E        | 2094-12-13 02:02:02 | 2082-12-24 01:01:01 |
|  4859 | Gl       | 2040-10-16 02:02:02 | 2051-10-25 01:01:01 |
| 21932 | GelDJbuE | 2017-11-26 02:02:02 | 2075-11-19 01:01:01 |
+-------+----------+---------------------+---------------------+

10 条数据全部正常入库,包括 2082、2094、2099 等高年份时间,验证了问题确实出在反斜杠转义字符上。

五、总结

  1. Out of range value报错,不一定为数值越界,优先核查原始数据文件。
  2. 排查文本隐藏字符可执行cat -A 文件名。
  3. LOAD数据加载排错需优先查阅.trc追踪日志。

本文为实操踩坑记录,仅供技术交流。

评论

登录后才可以发表评论
小熊发表于 1个月前
格式错误,应该是Data truncated的错误
用户头像
GBase用户28017发表于 1个月前
这个问题值得收藏。