Oracle Sql Loader“;ORA-01722:无效编号“;加载带有Windows行结尾的CSV文件时

Oracle Sql Loader“;ORA-01722:无效编号“;加载带有Windows行结尾的CSV文件时,oracle,sql-loader,Oracle,Sql Loader,我正在使用Linux shell中的Oracle Sql Loader实用程序将csv数据加载到Oracle DB中。 但我注意到,如果源csv文件的行尾是'\r\n'(Windows格式),sqlldr将无法加载最后一列的数据 例如,如果最后一列是FLOAT类型(在ctl文件中定义为“FLOAT EXTERNAL”),sqlldr将失败,并显示“ORA-01722:无效数字”: Sqlldr ctl文件: OPTIONS(silent=(HEADER)) load data replace

我正在使用Linux shell中的Oracle Sql Loader实用程序将csv数据加载到Oracle DB中。 但我注意到,如果源csv文件的行尾是'\r\n'(Windows格式),sqlldr将无法加载最后一列的数据

例如,如果最后一列是FLOAT类型(在ctl文件中定义为“FLOAT EXTERNAL”),sqlldr将失败,并显示“ORA-01722:无效数字”:

Sqlldr ctl文件:

OPTIONS(silent=(HEADER))
load data
 replace
 into table fp_basic_bd
 fields terminated by "|" optionally enclosed by '"'
 TRAILING NULLCOLS
 (
 FS_PERM_SEC_ID CHAR(20),
 "DATE" DATE "YYYY-MM-DD", 
 ADJDATE DATE "YYYY-MM-DD", 
 CURRENCY CHAR(3),
 P_PRICE FLOAT EXTERNAL,
 P_PRICE_OPEN FLOAT EXTERNAL,
 P_PRICE_HIGH FLOAT EXTERNAL,
 P_PRICE_LOW FLOAT EXTERNAL,
 P_VOLUME FLOAT EXTERNAL
 )
sqlldr执行命令:

sqlldr -userid XXX -data ./test.data -log ./test.log -bad ./test.errors -control test.ctl -errors 3 -skip_unusable_indexes -skip_index_maintenance
sqlldr错误日志:

   Column Name                  Position   Len  Term Encl Datatype
------------------------------ ---------- ----- ---- ---- ---------------------
FS_PERM_SEC_ID                      FIRST    20   |  O(") CHARACTER            
"DATE"                               NEXT     *   |  O(") DATE YYYY-MM-DD      
ADJDATE                              NEXT     *   |  O(") DATE YYYY-MM-DD      
CURRENCY                             NEXT     3   |  O(") CHARACTER            
P_PRICE                              NEXT     *   |  O(") CHARACTER            
P_PRICE_OPEN                         NEXT     *   |  O(") CHARACTER            
P_PRICE_HIGH                         NEXT     *   |  O(") CHARACTER            
P_PRICE_LOW                          NEXT     *   |  O(") CHARACTER            
P_VOLUME                             NEXT     *   |  O(") CHARACTER            

value used for ROWS parameter changed from 300000 to 65534
Record 1: Rejected - Error on table FP_BASIC_BD, column P_VOLUME.
ORA-01722: invalid number

Record 2: Rejected - Error on table FP_BASIC_BD, column P_VOLUME.
ORA-01722: invalid number
当我将Windows行结尾替换为Unix行结尾时,所有错误都消失了,所有数据都正确加载

我的问题是:如何在sqlldr配置文件中指定行终止符char,但仍将源文件名保留在shell命令中

我看过一些关于如何使用流记录格式的示例, 但这些示例不适用于我的情况,因为我需要在shell命令中保留数据文件的名称,而不是在ctl文件中。

尝试使用并指定终止符字符串。从文件中

在基于UNIX的平台上,如果未指定终止符\u字符串,则SQL*加载器默认为换行符,\n


终止符字符串应该允许您指定字符的组合。

我最近在通过csv文件将数据加载到表中时遇到了相同的问题。 我的文件如下所示:

LOAD DATA
    infile '/ipoapplication/utl_file/LBR_HE_Mar16.csv'
    REPLACE
    INTO TABLE LOAN_BALANCE_MASTER_INT
    fields terminated by ',' optionally enclosed by '"'
    (
    ACCOUNT_NO,
    CUSTOMER_NAME,
    LIMIT,
    REGION,

    TERM_AGREEMENT INTEGER EXTERNAL
    )
正如你提到的,我一直收到相同的错误“无效号码” 事实证明,这种情况经常发生 -当列数据类型为数字,但从csv文件获取的数据为字符串时,oracle loader无法执行字符串到数字的转换。 -当csv文件中的字段被一些分隔符(如空格、制表符等)终止时

以下是我更改ctl文件的方式:

 LOAD DATA
    infile '/ipoapplication/utl_file/LBR_HE_Mar16.csv'
    REPLACE
    INTO TABLE LOAN_BALANCE_MASTER_INT
    fields terminated by ',' optionally enclosed by '"'
    (
    ACCOUNT_NO,
    CUSTOMER_NAME,
    LIMIT,
    REGION,

    TERM_AGREEMENT INTEGER Terminated by Whitespace
    )

使用
dos2unix-urfilename-urfilename
进行到unix的下线转换,然后
sqlldr
应该可以工作?是的,这是我目前处理这个问题的方式。但源数据量太大(每天高达40GB),我正在尝试尽快加载数据。因此,我正在寻找方法,使它只通过sqlldr,而不需要额外的预编辑输入CSV文件。流记录格式迫使开发人员将输入文件名保存在ctl文件中。这不是我真正需要的解决方案,我需要将输入文件名保留在shell命令中(请参阅我的问题)。您的修复工作正常,但我们必须使用“TERM_AGREEMENT INTEGER外部以空格终止”