jdbc时区

在jOOQ邮件列表上,最近有一个有趣的讨论,关于jOOQ当前缺乏对TIMESTAMP WITH TIME ZONE数据类型的现成支持。

没有人说日期,时间和时区很容易! 这里有一个有趣的文章,我建议阅读: 虚假的程序员相信时间

当那还不够时,还请阅读: 更多的虚假程序员相信时间

我个人喜欢程序员错误地认为“ Unix时间是自1970年1月1日以来的秒数”。 …Unix时间无法代表leap秒;)

返回JDBC

这是Jaybird开发人员(Firebird JDBC驱动程序) Mark Rotteveel提出的一个有趣的Stack Overflow答案: java.sql.Timestamp时区是否特定?

可以按照以下方式观察Mark的解释(我在这里使用PostgreSQL):

Connection c = getConnection();
Calendar utc = Calendar.getInstance(TimeZone.getTimeZone("UTC"));try (PreparedStatement ps = c.prepareStatement("select"+ "  ?::timestamp,"+ "  ?::timestamp,"+ "  ?::timestamp with time zone,"+ "  ?::timestamp with time zone"
)) {ps.setTimestamp(1, new Timestamp(0));ps.setTimestamp(2, new Timestamp(0), utc);ps.setTimestamp(3, new Timestamp(0));ps.setTimestamp(4, new Timestamp(0), utc);try (ResultSet rs = ps.executeQuery()) {rs.next();System.out.println(rs.getTimestamp(1) + " / " + rs.getTimestamp(1).getTime());System.out.println(rs.getTimestamp(2, utc)+ " / " + rs.getTimestamp(2, utc).getTime());System.out.println(rs.getTimestamp(3) + " / " + rs.getTimestamp(3).getTime());System.out.println(rs.getTimestamp(4, utc)+ " / " + rs.getTimestamp(4, utc).getTime());}
}

上面的程序使用Java和DB中使用时区而不使用时区的所有排列,并且输出始终相同:

1970-01-01 01:00:00.0 / 0
1970-01-01 01:00:00.0 / 0
1970-01-01 01:00:00.0 / 0
1970-01-01 01:00:00.0 / 0

如您所见,在每种情况下,UTC时间戳0均已正确存储并从数据库中检索到。 我自己的语言环境是瑞士,即CET / CEST,在Epoch是UTC + 1,这是在Timestamp.toString()上获得的输出。

当您在SQL和/或Java中使用时间戳文字时,事情会变得很有趣。 如果这样替换绑定变量:

Timestamp almostEpoch = Timestamp.valueOf("1970-01-01 00:00:00");ps.setTimestamp(1, almostEpoch);
ps.setTimestamp(2, almostEpoch, utc);
ps.setTimestamp(3, almostEpoch);
ps.setTimestamp(4, almostEpoch, utc);

这又是我在CET / CEST上获得的机器上的东西

1970-01-01 00:00:00.0 / -3600000
1970-01-01 00:00:00.0 / -3600000
1970-01-01 00:00:00.0 / -3600000
1970-01-01 00:00:00.0 / -3600000

即不是Epoch,而是我首先发送到服务器的时间戳文字。 请注意,绑定/获取的四种组合仍然始终产生相同的时间戳。

让我们看看如果写入数据库的会话使用与从数据库获取会话不同的时区(假设您在PST中)(我再次使用CET或UTC),会发生什么。 我正在运行此程序:

Calendar utc = Calendar.getInstance(TimeZone.getTimeZone("UTC"));Calendar pst = Calendar.getInstance(TimeZone.getTimeZone("PST"));try (PreparedStatement ps = c.prepareStatement("select"+ "  ?::timestamp,"+ "  ?::timestamp,"+ "  ?::timestamp with time zone,"+ "  ?::timestamp with time zone"
)) {ps.setTimestamp(1, new Timestamp(0), pst);ps.setTimestamp(2, new Timestamp(0), pst);ps.setTimestamp(3, new Timestamp(0), pst);ps.setTimestamp(4, new Timestamp(0), pst);try (ResultSet rs = ps.executeQuery()) {rs.next();System.out.println(rs.getTimestamp(1)+ " / " + rs.getTimestamp(1).getTime());System.out.println(rs.getTimestamp(2, utc)+ " / " + rs.getTimestamp(2, utc).getTime());System.out.println(rs.getTimestamp(3)+ " / " + rs.getTimestamp(3).getTime());System.out.println(rs.getTimestamp(4, utc)+ " / " + rs.getTimestamp(4, utc).getTime());}
}

它产生以下输出:

1969-12-31 16:00:00.0 / -32400000
1969-12-31 17:00:00.0 / -28800000
1970-01-01 01:00:00.0 / 0
1970-01-01 01:00:00.0 / 0

第一个时间戳记是将Epoch存储为PST(16:00),然后数据库中删除了时区信息,这将Epoch转换为您在Epoch处的本地时间(-28800秒/ -8h),即真的存储了。

现在,当我从自己的时区CET获取此时间时,我仍然想要获取当地时间(16:00)。 但是在我的时区,这不再是-28800秒,而是-32400秒(-9h)。 够古怪吗?

当我获取存储的本地时间(16:00)时,事情反过来了,但是我强迫获取发生在UTC中,这将产生您存储的时间戳,最初是PST(-28800)秒)。 但是,在我的时区CET中打印此时间戳(-28800秒)时,现在是17:00。

当我们在数据库中使用TIMESTAMP WITH TIME ZONE数据类型时,将保持时区(PST),并且当我获取Timestamp值时,无论使用CET还是UTC,我仍然会得到Epoch,它已安全地存储到了数据库,在CET中打印为01:00。

ew。

TL; DR:

使用jOOQ时 ,如果正确的UTC时间戳对您很重要,请使用TIMESTAMP WITH TIMEZONE,但是您必须实现自己的数据类型Binding ,因为jOOQ当前不支持该数据类型。 一旦使用了自己的数据类型Binding,就可以使用Java 8的time API,它比java.sql.Timestamp +丑陋的Calendar更好地表示了这些不同的类型。

如果当地时间对您很重要,或者您不在跨时区工作,则可以使用TIMESTAMP和jOOQ的Field <Timestamp>。

幸运的是,如果您像我一样,可以在一个只有一个时区的很小的国家/地区进行操作,而大多数本地软件都不会遇到此问题。

翻译自: https://www.javacodegeeks.com/2015/07/whats-even-harder-than-dates-and-timezones-dates-and-timezones-in-sql-jdbc.html

jdbc时区

jdbc时区_什么比日期和时区更难? SQL / JDBC中的日期和时区!相关推荐

  1. SQL Server中的日期和时间:DATEADD()

    我们现在处于SQL Server和Azure SQL数据库中关于日期和时间的长篇系列的主页. 本周我们将讨论日期和时间中我最喜欢的T-SQL函数之一:  DATEADD(). 句法 与类似的功能一样, ...

  2. sql server中对日期字段值的比较

    本文转自:http://www.cnblogs.com/feison/articles/166981.html sql server中对日期字段的比较方式有多种,介绍几种常用的方式: 用northwi ...

  3. 日期类的加减及java中所以日期类的操作算法大全

    1.计算某一月份的最大天数 1Calendar time=Calendar.getInstance(); 2time.clear(); 3time.set(Calendar.YEAR,year); / ...

  4. SQL Server中的日期时间类型

    一. 数据类型 SQL Server008在上一个版本的基础上把日期时间类的数据类型增加到了六个.除了SQL Server2005的datetime和smalltime之外,加了date,dateti ...

  5. 日期如何比较 java_如何比较Java中的日期?

    Basil Bourqu.. 30 TL;博士 LocalDate today = LocalDate.now( ZoneId.of( "America/Montreal" ) ) ...

  6. python日期选择框_Python的Django框架中设置日期和字段可选的方法

    设置字段可选 在摆弄了一会之后,你或许会发现管理工具有个限制:编辑表单需要你填写每一个字段,然而在有些情况下,你想要某些字段是可选的. 举个例子,我们想要Author模块中的email字段成为可选,即 ...

  7. SQL查询中的日期比较

    在不同的数据库中,时间的比较也许不同,但是通过hibernate统一封装起来. java.util.Date begin, end; String sql = "from demo wher ...

  8. oracle sql 格式化日期,怎么在 SQL Server中 将日期格式化

    to_date()是Oracle数据库函数的代表函数之一,下文对Oracle to_date()函数的几种用法作了详细的介绍说明,需要的朋友可以参考下 在Oracle数据库中,Oracle to_da ...

  9. html日期写入数据库,javascript – 在HTML5 Web SQL数据库中对日期时间进行排序

    我无法找到解决问题的方法. 我有一个HTML5 Web SQL数据库,其表格如下: db.transaction(function(tx) { tx.executeSql("CREATE T ...

  10. java自动依照日期建表,脚本根据一个表中的日期字段填充每月汇总表

    你想在这里做两件事 . 我假设您正在使用Oracle(因为您正在使用Java) . 首先,您希望对每个用户的每日交易进行分组 . 创建一个名为 tempTable 的临时表 . 使用 to_char( ...

最新文章

  1. 操作系统课设--具有优先级的线程调度
  2. 【面向对象】面向对象程序设计测试题13-Java异常处理测试题
  3. 10大开源文档管理系统_开源文档的5大趋势
  4. Redis 6 将采用全新协议 RESP3,以提供客户端缓存功能
  5. WWDC20中iOS的改变
  6. 蓝屏代码查询器1.1.8
  7. cdrx8如何批量导出jpg_Coreldraw/CDR X8 存低版本打开问题 – 数码打印破图 – Coreldraw/CDR软件崩溃 – 渐变导位图角度变了...
  8. java订餐管理系统代码,基于JAVA的订餐管理系统
  9. 圆柱体积怎么算立方公式_圆柱的体积换算立方怎么算
  10. 【酷毙了】野火新版fireTools多功能调试助手,有Windows和Linux版本,就问你喜不喜欢。...
  11. 电脑误格式化的数据怎么恢复,误格式化数据恢复教程
  12. 程序发生run time error原因及解决方案
  13. [计算机数值分析]四阶龙格-库塔经典格式解常微分方程的初值问题
  14. 测试工程师需要具备的能力
  15. 如何查看手机登录IP地址
  16. GDOC CEO Musk Shing出席“链接未来”区块链全球人才交流会
  17. java Web 前后端交互
  18. 2013-8-17 上周工作总结
  19. vc++ 调用winapi调节屏幕亮度
  20. web前端-html-css-字体的分类(serif衬线、sans-serif非衬线、monospace等宽、cursive草书、fantasy虚幻)

热门文章

  1. CF666E-Forensic Examination【广义SAM,线段树合并】
  2. ARC122C-Calculator【乱搞,构造】
  3. 牛客练习赛69D-火柴排队【dp】
  4. 15、java中的集合(2)
  5. 博客文章列表(一)——JAVA
  6. Spark入门(一)单主standalone安装
  7. 解决mybatis generator无法覆盖XML
  8. 深入理解分布式系统中的缓存架构(上)
  9. 我猜,每个程序员对着电梯都想过调度算法吧
  10. JDK 5 ~ 10 新特性倾情整理