Oracle DB Ora-01839:指定月份的日期无效。 29-02-2016 闰年
Oracle DB Ora-01839: date not valid for month specified. 29-02-2016 leap year
我们都知道今天是个特别的日子。它是 闰年 的 29th of February 2016
。
我们从 Oracle 数据库中的某些表收到错误消息。错误是:Oracle ORA-01839: date not valid for month specified
.
例如发生错误的简单select:select * from table where table_date > sysdate -0.1;
对于其他表,这个 select 没有问题,只是对于某些表。
有办法解决这个问题吗?因为我们今天不能使用很多表。
我们正在使用 Oracle 12c
。
经过深入研究,很清楚为什么我们的一些选择今天不起作用。该错误是由关键字 interval
引起的,这是一个已知问题。 (或者 ANSI/ISO spec 说它应该如何工作,第 205 页底部/第 206 页顶部)
这是来自 oracle community blog 的引述:
问题:
select to_date('2012-feb-29','yyyy-mon-dd') + interval '1' year as dt from dual;
ORA-01839: date not valid for month specified
01839. 00000 - "date not valid for month specified"
*Cause:
*Action:
select to_date('2012-feb-29','yyyy-mon-dd') + interval '2' year as dt from dual;
ORA-01839: date not valid for month specified
01839. 00000 - "date not valid for month specified"
*Cause:
*Action:
select to_date('2012-feb-29','yyyy-mon-dd') + interval '3' year as dt from dual;
ORA-01839: date not valid for month specified
01839. 00000 - "date not valid for month specified"
*Cause:
*Action:
select to_date('2012-feb-29','yyyy-mon-dd') + interval '4' year as dt from dual;
29-FEB-16 00:00:00
select to_date('2012-feb-29','yyyy-mon-dd') + interval '1' day as dt from dual;
01-MAR-12 00:00:00
select to_date('2012-feb-29','yyyy-mon-dd') + interval '1' month as dt from dual;
29-MAR-12 00:00:00
回答:
That's just how INTERVALs work. Leap years are the least of the
problem; adding 1 month to March 31 results in the same error. If you
want to make sure that the result is a valid DATE, then use
ADD_MONTHS. (There's no separate function for adding years; use
ADD_MONTH (SYSDATE, 12*n) to get the DATE that is n years from now.)
为什么会发生在我们的案例中:
在我们的案例中,出于安全原因,我们对某些表使用了虚拟专用数据库。我们在大多数选择中应用了 interval
关键字。
改为做什么:
改用ADD_MONTHS
。
select add_months(to_date('2012-feb-29','yyyy-mon-dd'), 12) as dt from dual;
我们都知道今天是个特别的日子。它是 闰年 的 29th of February 2016
。
我们从 Oracle 数据库中的某些表收到错误消息。错误是:Oracle ORA-01839: date not valid for month specified
.
例如发生错误的简单select:select * from table where table_date > sysdate -0.1;
对于其他表,这个 select 没有问题,只是对于某些表。
有办法解决这个问题吗?因为我们今天不能使用很多表。
我们正在使用 Oracle 12c
。
经过深入研究,很清楚为什么我们的一些选择今天不起作用。该错误是由关键字 interval
引起的,这是一个已知问题。 (或者 ANSI/ISO spec 说它应该如何工作,第 205 页底部/第 206 页顶部)
这是来自 oracle community blog 的引述:
问题:
select to_date('2012-feb-29','yyyy-mon-dd') + interval '1' year as dt from dual;
ORA-01839: date not valid for month specified
01839. 00000 - "date not valid for month specified"
*Cause:
*Action:
select to_date('2012-feb-29','yyyy-mon-dd') + interval '2' year as dt from dual;
ORA-01839: date not valid for month specified
01839. 00000 - "date not valid for month specified"
*Cause:
*Action:
select to_date('2012-feb-29','yyyy-mon-dd') + interval '3' year as dt from dual;
ORA-01839: date not valid for month specified
01839. 00000 - "date not valid for month specified"
*Cause:
*Action:
select to_date('2012-feb-29','yyyy-mon-dd') + interval '4' year as dt from dual;
29-FEB-16 00:00:00
select to_date('2012-feb-29','yyyy-mon-dd') + interval '1' day as dt from dual;
01-MAR-12 00:00:00
select to_date('2012-feb-29','yyyy-mon-dd') + interval '1' month as dt from dual;
29-MAR-12 00:00:00
回答:
That's just how INTERVALs work. Leap years are the least of the problem; adding 1 month to March 31 results in the same error. If you want to make sure that the result is a valid DATE, then use ADD_MONTHS. (There's no separate function for adding years; use ADD_MONTH (SYSDATE, 12*n) to get the DATE that is n years from now.)
为什么会发生在我们的案例中:
在我们的案例中,出于安全原因,我们对某些表使用了虚拟专用数据库。我们在大多数选择中应用了 interval
关键字。
改为做什么:
改用ADD_MONTHS
。
select add_months(to_date('2012-feb-29','yyyy-mon-dd'), 12) as dt from dual;