【问题标题】:How to convert timestamp from different timezones in Hive如何在 Hive 中转换不同时区的时间戳
【发布时间】:2019-02-22 01:27:28
【问题描述】:

我正在使用 json 有效负载查询 Hive 中的表,并从这些有效负载中提取时间戳。问题是时间戳以不同的时区格式存在,我试图在我的时区中提取它们。

我目前正在使用以下内容:

选择
from_unixtime(unix_timestamp(get_json_object (table.payload, '$.timestamp'), "yyyy-MM-dd'T'HH:mm:ss.SSSXXX"))
来自表

如果时间戳采用以下格式,则返回正确的值:2018-08-16T08:54:05.543Z --> 2018-08-16 18:54:05(更改格式并转换为我的时区)

但是,如果有效负载包含以下格式的时间戳,则上述查询返回“null”: 2018-09-13T01:35:08.460+0000 2018-09-13T11:35:09+10:00

如何调整我的查询以适用于所有类型的时间戳,所有时间戳都转换为正确的时区(+10 是我的时区!)并且都采用相同的格式?

提前致谢!

【问题讨论】:

  • 您将需要一个非常复杂的 CASE WHEN 逻辑与正则表达式匹配/替换,以处理大多数格式(并且不要期望处理所有 - 您需要有关区域设置的信息以匹配 DEC/DEZ或 01/02 作为 1 月 2 日与 2 月 1 日)。如果您无法开发 Java UDF,请创建一个 TEMPORARY MACRO

标签: hive timezone timestamp


【解决方案1】:

下面的宏怎么样:

create temporary macro extract_ts(ts string) 
  from_unixtime(unix_timestamp(regexp_extract(ts, '(.*)\\+(.*)', 1), "yyyy-MM-dd'T'HH:mm:ss") + 3600*cast(regexp_extract(ts, '(.*)\\+(.*)\\:(.*)', 2) as int));

例如,

hive> select extract_ts('2018-09-13T11:35:09+10:00');
OK
2018-09-13 21:35:09

【讨论】:

  • 不处理表示为“+1000”或“Z”或“UTC”的时区
  • 通过case when 添加额外的解析器并不难,我只需要完整的时间戳格式列表。
【解决方案2】:

如果没有正则表达式,使用 Z 表示 +1000 的 XXX 表示 +10:00:

select unix_timestamp('2016-07-30T10:29:33.000+03:00', "yyyy-MM-dd'T'HH:mm:ss.SSSXXX") as t1
select unix_timestamp('2016-07-30T10:29:33.000+0300', "yyyy-MM-dd'T'HH:mm:ss.SSSZ") as t2

关于时间格式的完整文档: https://docs.oracle.com/javase/7/docs/api/java/text/SimpleDateFormat.html

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-11-23
    • 1970-01-01
    • 2020-10-17
    • 2013-04-15
    • 2016-01-17
    • 2019-10-07
    • 1970-01-01
    相关资源
    最近更新 更多