Now()没有时区

アレッ*_*ックス 57 postgresql timestamp postgresql-9.2

我有一个added_at类型的列timestamp without time zone.我希望它的默认值是当前的日期时间但没有时区.该函数也now()返回一个时区.

我该如何解决这个问题?

Erw*_*ter 67

SELECT now()::timestamp
Run Code Online (Sandbox Code Playgroud)

就这样.演员表将时间戳转换为您时区的当前时间戳.这也是Postgres中标准SQL函数LOCALTIMESTAMP的实现方式.

如果您不在多个时区操作,那就可以了.否则切换到timestamptzadded_at.区别?

  • @DmitriKosolobov:`now()`已经返回`timestamptz`,因此`now():: timestamptz`没有做任何有用的事情. (3认同)
  • @ThoPaz:`now() AT TIME ZONE 'UTC'`返回时区UTC的本地时间。`LOCALTIMESTAMP` 或 `now()::timestamp` 返回会话当前 `timezone` 设置的本地时间。两种不同的东西!仅当当前会话以“timezone = 'UTC'”运行时才会返回相同的值。 (2认同)

Ric*_*ton 36

那么你可以这样做:

SELECT now() AT TIME ZONE current_setting('TimeZone');
SELECT now() AT TIME ZONE 'Europe/Paris';
SELECT now() AT TIME ZONE 'UTC';
Run Code Online (Sandbox Code Playgroud)

不确定这对于"added_at"列是否有意义.您几乎总是希望绝对时间戳(带时区的时间戳)不是浮动时间戳.


编辑以下几点的回复:

  1. 是的,应该使用带时区(绝对时间)的时间戳,除非你有充分的理由不这样做.

  2. 客户端时区由SHOW TimeZonecurrent_setting(...)如上所示给出.

需要一些时间来浏览手册 - 它们很好地涵盖了所有这些.


Mil*_*dev 17

"当前日期/时间":

CURRENT_TIME和CURRENT_TIMESTAMP提供带时区的值; LOCALTIME和LOCALTIMESTAMP提供没有时区的值.


Kaz*_*Kaz 5

2020 年新的原生答案

在 PostgreSQL 中,如果您只想通过不带时区的调用来获取当前日期时间,以及秒字段中小数点后面的CURRENT_TIMESTAMP() 小数位?

(在 PostgreSQL v12.4 上测试)

然后使用这个:

SELECT CURRENT_TIMESTAMP(0)::TIMESTAMP WITHOUT TIME ZONE;
Run Code Online (Sandbox Code Playgroud)

如果您将列的数据类型定义为timestamp(而不是timestamptz),那么您可以存储没有时区的时间戳,在这种情况下您不需要添加TIMESTAMP WITHOUT TIME ZONE

像这样:

CREATE TABLE foo (created timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP(0))
Run Code Online (Sandbox Code Playgroud)

在上面的函数中,传递 0 来去掉秒字段中的小数位。