并发查询以在Oracle的分区表中插入数据

时间:2018-10-26 04:54:51

标签: oracle plsql partitioning database-administration oracle11gr2

我正在通过ETL工具运行并发插入查询(同时进行12个查询),以将数据插入Oracle的分区表中。

表定义为

CREATE TABLE CUST_TRAN
(
TRAN_SEQ_NO NUMBER(20,0)
, TRAN_DATE DATE
) 
TABLESPACE USERS
STORAGE (INITIAL 256K NEXT 256K)
PARTITION BY RANGE (TRAN_DATE) 
INTERVAL(NUMTODSINTERVAL(1, 'DAY')) 
(  
   PARTITION CUST_TRAN_p_old VALUES LESS THAN (TO_DATE('1-1-2008', 'DD-MM-YYYY'))
)

这12个查询在4个不同的日期运行(每个日期3个查询)。因此,这12个查询正试图插入4个分区中。这是示例插入查询-

insert into cust_tran 
select a.tran_seq_no, trunc(a.tran_datetime) as tran_date
from table_a a
    inner join table_b b on a.store = b.store
        and a.tran_seq_no = b.tran_seq_no
        and trunc(a.tran_datetime) = to_date('2018-01-31', 'YYYY-MM-DD')
        and a.tran_type in ('SALE')

但是,我一直遇到以下问题之一-

1)我收到此错误-ORA-14300: partitioning key maps to a partition outside maximum permitted number of partitions

2)作业运行正常,没有任何错误,但是将数据插入到CUST_TRAN_SUMM_p_old分区中,该日期具有任何源查询中都不存在的奇异日期,并且该日期在源表中不存在。奇怪的日期的确切值很难分辨,因为当我使用SQL Developer并将日期格式设置为YYYY-MM-DD HH24:MI:SS(在“工具”>“首选项”>“数据库”>“ NLS”中)时,它显示为空,但当我将显示格式更改为DD-MON-RR HH24:MI:SS时,它显示29-NOV-01 22:58:59。当我使用DBeaver时,它显示为10101-11-29 22:58:59。当我使用Toad for Oracle时,它显示为1/1/0001。

第一个问题真的很奇怪,因为我在过滤器中提供了日期,而且它无法获取不在过滤器中的另一个日期。另外,我是在重新创建表后运行此程序。因此,不可能达到最大分区数(1,023,999)。

第二个问题也很奇怪。

这是Oracle中的错误吗? Oracle中是否有一些需要更改的设置?使用并发插入查询将数据插入分区表是否错误?

1 个答案:

答案 0 :(得分:0)

至少一件事似乎很清楚。您提到的错误是

 ORA-14300: partitioning key maps to a partition outside maximum permitted number of partitions

在间隔分区表的分区键中插入值NULL时发生。

简单尝试一下此插入

 insert into CUST_TRAN (TRAN_SEQ_NO,TRAN_DATE) Values(1,null); 

此问题没有简单的解决方法,通常使用一些奇怪的日期(例如01.01.2999)来代替缺少的日期-例如,参见here

在这里,我将开始调查-假设您观察到的奇怪的日期可以替代无效日期的缺失。

调查源数据库还不够,典型的ETL过程比简单的插入要复杂得多。您必须检查ETL脚本的代码,以查看是否有这种日期操作。

到您的观察日期10101-11-29-允许的range for years排除10101作为一年。

  

Oracle数据库可以存储儒略时代的日期,范围是从公元前4712年1月1日到9999年12月31日(通用时代或“ AD”)。除非特别使用BCE(格式掩码中的“ BC”),否则默认为CE日期条目。

从事实来看,该日期位于old分区中(即小于2008年),因此我认为它是29年11月-DATE'0029-11-01',而DAY则是在输出中与其他字符串串联