如何最好地在 PostgreSQL 中存储时间戳?

Bam*_*Bam 32 postgresql datatypes timestamp utc-time timezone

我正在研究 PostgreSQL 数据库设计,我想知道如何最好地存储时间戳。

假设

不同时区的用户将使用数据库执行所有 CRUD 功能。

我查看了 2 个选项:

  • timestamp NOT NULL DEFAULT (now() AT TIME ZONE 'UTC')

  • bigint NOT NULL DEFAULT

因为timestamp我会发送一个字符串来表示 INSERT 时刻的确切(UTC)时间戳。

因为bigint我会存储完全相同的东西,但以数字格式存储。(时区问题是在将毫秒移交给服务器之前处理的,因此总是以 UTC 为单位的毫秒。)

存储 a 的一个主要优点bigint可能是它更容易存储和检索,因为传递正确格式的时间戳比简单的数字(自 Unix Epoc 以来的毫秒)更复杂。

我的问题是哪种方法可以实现最灵活的设计,以及每种方法可能存在哪些缺陷。

Erw*_*ter 31

将时间戳存储为timestamp,或者更确切地说timestamptz( timestamp with time zone),因为您要处理多个时区。这会强制执行有效数据并且通常是最有效的。一定要理解数据类型,有一些误解:

解决您的顾虑:

传递正确格式的时间戳比简单的数字更复杂

如果您愿意,您可以通过任何一种方式传递和检索 UNIX 纪元:

SELECT to_timestamp(1437346800)
     , extract(epoch FROM timestamptz '2015-07-20 01:00+02');
Run Code Online (Sandbox Code Playgroud)

有关的:

如果要存储写入数据库的当前时间戳,请使用timestamptz 具有默认值now()。数据库服务器上的系统时间通常比多个客户端提交各自的时间概念更可靠和一致。
因为INSERT它可以很简单:

CREATE TABLE foo (
  ... -- other columns
, created_at timestamptz NOT NULL DEFAULT now()
);
Run Code Online (Sandbox Code Playgroud)

只是不要写信给那个专栏。它是自动填充的。


dno*_*eth 10

您应该始终以其本机数据类型存储数据,以便您可以使用内置函数。时间戳的数据类型是:timestamp

顺便说一句,一个timestamp存储为一个字符串,它存储为8字节整数,完全一样bigintPostgreSQL文档