Postgres UTC 时间戳?

fad*_*bee 0 sql postgresql timestamp

我想要几个表中的 UTC 时间戳“创建”字段。

ts TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT now(),给我带有时区的当地时间:

foo=# select ts from messages;
              ts               
-------------------------------
 2017-05-26 11:54:07.532796+01
 2017-05-26 11:54:08.536241+01
 2017-05-26 11:54:09.538119+01
 2017-05-26 11:54:10.541089+01
 2017-05-26 11:54:11.543262+01
Run Code Online (Sandbox Code Playgroud)

ts TIMESTAMP NOT NULL DEFAULT now(),给我没有时区信息的当地时间(危险):

foo=# select ts from messages;
             ts             
----------------------------
 2017-05-26 11:56:00.134596
 2017-05-26 11:56:01.13798
 2017-05-26 11:56:02.140586
 2017-05-26 11:56:03.143076
 2017-05-26 11:56:04.14565
Run Code Online (Sandbox Code Playgroud)

当代码在非 UTC 时区(例如 BST,英国夏令时间)的服务器上运行时,什么字段定义将为我提供以下内容:

foo=# select ts from messages;
             ts             
----------------------------
 2017-05-26 10:56:00.134596+00
 2017-05-26 10:56:01.13798+00
 2017-05-26 10:56:02.140586+00
 2017-05-26 10:56:03.143076+00
 2017-05-26 10:56:04.14565+00
Run Code Online (Sandbox Code Playgroud)

甚至:

foo=# select ts from messages;
             ts             
----------------------------
 2017-05-26 10:56:00.134596
 2017-05-26 10:56:01.13798
 2017-05-26 10:56:02.140586
 2017-05-26 10:56:03.143076
 2017-05-26 10:56:04.14565
Run Code Online (Sandbox Code Playgroud)

如果没有其他可能的话,那就没问题了(注意:上面两个例子中的时间都是 UTC 上午 10 点,而不是 BST 上午 11 点)。

Vao*_*sun 7

带时区的时间戳是您的选择:

t=# select now();
              now
-------------------------------
 2017-05-26 11:04:19.240294+00
(1 row)

t=# set timezone to 'EET';
SET
t=# select now();
              now
-------------------------------
 2017-05-26 14:04:45.749123+03
(1 row)
Run Code Online (Sandbox Code Playgroud)

但如果你插入 select now() 它将节省 UTC 时间,你可以检查:

t=# select now() at time zone 'utc';
          timezone
----------------------------
 2017-05-26 11:05:01.045544
(1 row)
Run Code Online (Sandbox Code Playgroud)

https://www.postgresql.org/docs/current/static/datatype-datetime.html#DATATYPE-TIMEZONES

所有时区感知的日期和时间均以 UTC 内部存储。在显示给客户端之前,它们会转换为 TimeZone 配置参数指定的区域中的本地时间。