数十万行的触发器 updatedAt=NOW() 将不实际

0 postgresql trigger

updatedAt如果在 PG 9.6 中插入/更新了新数据,我将使用 SQL 触发器来更新列。

这是触发器将调用的函数

CREATE FUNCTION sp_updatedatstamp() RETURNS trigger AS $updatedat_stamp$
  BEGIN
    NEW."updatedAt" := now();
    RETURN NEW;
  END;
$updatedat_stamp$ LANGUAGE plpgsql;
Run Code Online (Sandbox Code Playgroud)

这是触发脚本

create trigger tg_de_installment_cdcupdatedat before
insert or update
    on
    public.table for each row execute procedure sp_updatedatstamp()
Run Code Online (Sandbox Code Playgroud)

这是表定义

CREATE TABLE table (
    id serial NOT NULL,
    "type" text NULL,
    "transactionDate" timestamptz NULL,
    remark text NULL,
    "createdAt" timestamptz NULL,
    "updatedAt" timestamptz NULL,
    "deletedAt" timestamptz NULL,
    CONSTRAINT table_pkey PRIMARY KEY (id)
);
Run Code Online (Sandbox Code Playgroud)

此代码适用于小数据,直到应用程序执行需要 30 分钟的批量更新查询(将更新 100K+ 行)。

触发器将使所有 100k+ 行使用updatedAt第一行,这会使其他行updatedAt不正确。最后,我们计划 5 分钟的数据管道将丢失这些数据。有没有办法让 SQL 触发器使用它的实际时间戳来处理大量数据?

a_h*_*ame 5

如手册中所述

由于这些函数返回当前事务的开始时间,因此它们的值在事务期间不会改变。这被认为是一个特性:其意图是允许单个事务具有一致的“当前”时间概念,以便同一事务内的多个修改具有相同的时间戳。

(强调我的)

因此,如果您希望每次调用都有不同的值,请使用 clock_timestamp()