开发反馈jdbc连接oracle时遇到报错 java.sql.SQLException: ORA-00604: error occurred at recursive SQL level 1 ORA-01882: timezone region not found。并且只有这一台应用服务器有这个问题,别的都是正常的。
网上搜索发现,通常是由于:Oracle数据库与应用的时区不一致导致的。
一、 常规解决方案
查看下JVM的时区,编写一个简单的CheckTz.java
import java.util.TimeZone;
public class CheckTz {
public static void main(String[] args) {
System.out.println(TimeZone.getDefault());
}
}
- 法一:修改java运行环境配置,添加-Duser.timezone=xxx(xxx为oracle时区ID)
- 法二:修改应用服务器时区,重新执行JVM初始化
cp /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
echo 'Asia/Shanghai' >/etc/timezone
Java可以通过Timezone获取时区,但是获取的时区是JVM初始化时保存的时区,并不是操作系统所设置的时区。当修改了操作系统的时区后,JVM并不会同步更新,因此还需要重新执行JVM初始化。
二、 ORA-01882相关bug
之前还遇到一个特定类型sql触发ora-1882报错的bug,sql的特征是通过dblink查询timestamp 字面值。
详情可以参考 Bug 16731148 ORA-1882 using TIMESTAMP literals over a database link
An unexpected ORA-1882 may be raised when using TIMESTAMP literals across a database link connection if the NLS_NUMERIC_CHARACTERS setting
does not use a dot (".") as the decimal separator.workaround
alter session set NLS_NUMERIC_CHARACTERS = ',.'; select timestamp '2012-07-24 07:00:00.00' from dual@somelink;
参考
https://blog.csdn.net/Loiterer_Y/article/details/107629659
https://blog.csdn.net/Hehuyi_In/article/details/85759200
Doc ID 16731148.8