ResultSet#getDate()语义

Phi*_*all 8 java oracle datetime jdbc

我们从已迁移ojdbc6-11.2.0.3.0到ojdbc7-12.1.0.1与观察到的变化ResultSet#getDate()语义.之前java.sql.Date通过根据指定的合同将小时,分钟,秒和毫秒设置为零,将返回"标准化" java.sql.Date.与ojdbc7此不再的情况下和java.sql.Date具有小时,分,秒和毫秒根据数据库上的值来设置.

我查看了Javadoc,ResultSet#getDate()并没有明确说出哪些行为是正确的.我会假设旧的行为符合规范的意图.我对吗?我们遇到过驱动程序错误吗?

Uwe*_*nus 11

这显然是一个错误,因为该类的文档java.sql.Date说明

为了符合SQL DATE的定义,java.sql.Date实例包含的毫秒值必须通过在与实例关联的特定时区中将小时,分钟,秒和毫秒设置为零来"标准化". .


小智 7

Oracle没有改变JDBC规范.我们更新了Oracle Database JDBC驱动程序文档.如果文档中有任何令人困惑或不正确的内容,我们将解决此问题.但是,没有更改JDBC规范.

以前版本的驱动程序不一致.在某些地方,他们将秒数归零.在其他地方他们没有.在12.1中,我们使驱动程序保持一致.问题是,什么是正确的行为.无论哪种方式,一些客户都会看到行为的变化.

经过长时间的激烈辩论,我们认为Oracle数据库客户最好的办法是不要将秒数归零.让我解释.

  • ANSI SQL DATE类型不存储秒.JDBC规范主要采用ANSI SQL.
  • Oracle Database DATE类型存储秒数.ANSI SQL委员会成员向我保证,这完全符合ANSI SQL.
  • JDBC的目标是公开数据库.JDBC规范没有定义一些抽象数据库,其目的是驱动程序实现该抽象数据库.JDBC驱动程序需要公开数据库的详细信息,而不是隐藏它们.JDBC定义了抽象一些数据库细节的工具,但程序员可以选择使用或不使用这些工具.
  • java.sql.Date虽然很容易,但不会强制执行零秒行为.该程序的责任在于强制执行或不强制执行该行为.

所以,Oracle DATE有几秒钟.Oracle JDBC驱动程序公开Oracle数据库.如果getDate秒为零,则会丢失数据.对于一些用户来说,这无关紧要,但对于其 由于Oracle DATE在DATE列中存储了许多Oracle数据库存储时间,并具有第二精度.在这些情况下将秒数归零会丢失信息.

如果程序通过非零秒的日期setDate,则程序创建了不合规的日期.如果驱动程序将秒数归零,则驱动程序会丢弃程序提供的信息以及数据库可以存储的信息.驾驶员再次失去了信息.

编写SQL或Java很容易将get和set的秒数归零.虽然肯定是可能的,但更难以解决丢失信息的问题.

因此我们选择让驾驶员始终保持秒数java.sql.Date.ResultSet.getDate可以构造一个java.sql.Date非零秒,但这准确地反映了数据库中的内容.如前所述,Date的实施可以强制执行,但没有.查看它的一种方法是程序在将数据存储在数据库中时创建了Date,因此它是程序的职责.驱动程序只是使用程序提供的数据.

我真的很抱歉以前司机不一致.我们一直在努力清理不一致和奇怪的角落案件.但我们拥有庞大的安装基础.每次我们改变某些东西,甚至是明显的错误修复,某些客户都会受到影响.因此,我们尝试在改进驱动程序和保持向后兼容性之间取得平衡.12c是主要版本.我们借此机会进行了一些更明显的变化.我们对这次中断感到遗憾,但认为这对整体客户来说是正确的.

  • jdbc规范说java.sql.Date没有时间组件(而不是java.sql.Timestamp).时间组件在许多业务环境中没有意义(例如,出生日期),并且此更改将导致在业务环境中使用此行为的现有应用程序在迁移到12c时中断.如果开发人员需要时间组件,则jdbc规范指示他们应该对DATE列使用get/setTimestamp()而不是get/setDate().最后,它可以节省时间,以确定更改列在驱动程序随附的README中的问题. (5认同)
  • 我知道这个话题是两年前提出的,但对我来说仍然是一个问题.有没有办法"说"ojdbc7在设置JVM参数的那一点上表现得像ojdbc6?这不是Oracle第一次破坏我公司的遗留代码从版本到版本进行此类更改(mapDateToTimestamp,J2EE13Compliant ......) (2认同)
  • "*但是认为这对整体客户来说是正确的做法" - 不,不是.它显然违反了JDBC规范.因此,Oracle(控制Java和JDBC规范)现在发布了一个甚至不符合JDBC的驱动程序. (2认同)