【问题标题】:Why does working on an individual POSTGRES partition effect the parent table?为什么在单个 POSTGRES 分区上工作会影响父表?
【发布时间】:2019-10-11 23:05:31
【问题描述】:

我有一个 24/7 的 postgres 数据库,我在其中对一些主要表进行了分区,以便在数据仍在加载时进行维护。不幸的是,对单个分区的更改似乎仍然会对父表产生影响。

我的表被定义为 -

CREATE TABLE tableA ( loadedTime TIMESTAMP, rawData CHARACTER(150))
PARTITION BY RANGE (loadedTime)

以及各个分区 -

CREATE TABLE tableA_yyyymmdd PARTITION OF tableA FOR VALUES FROM () TO ()

其中范围等于个别日期。

我有一个进程将记录24/7插入父表tableA(不是特定分区),loadedTime总是指当前时间,所以数据是总是被加载到今天的分区中。

为什么更改某些旧分区的表空间会导致插入当前分区超时?我的理解是分区几乎就像单独的表,我应该能够在分区上工作而不会导致父表出现问题 - 还是我误解了?

更新 - 当前使用 postgres 10.5。如果我尝试从父表中分离、真空和附加旧分区,我会遇到类似的问题。我可以在分离分区后访问父级,但是在分离/附加步骤期间,DETACH 和 ATTACH 需要一段时间,并且在父级超时时插入。

【问题讨论】:

  • 您使用的是 Postgres 10 还是 11?

标签: postgresql partitioning


【解决方案1】:

在 Postgres 10.5 中,父表上的INSERT 在确定应将给定行插入哪个分区之前锁定所有分区。如果您锁定了其中一个较旧的分区以更改其表空间,那么INSERT 必须等待锁定该分区,这可能解释了它超时的原因。 Postgres 11 具有相同的行为,但 Postgres 12(目前处于测试阶段)修复了这个问题,以便父表上的 INSERT 不会阻塞旧分区上的操作,反之亦然,也就是说,如果 INSERT只针对最新的分区。

ATTACHDETACH 命令锁定父表。因此,如果您在附加或分离分区的同时INSERTing 进入父表,则前者可能会被阻塞,直到后者完成。 ATTACH 可能需要一段时间,因为它必须扫描正在附加的分区以检查它是否不包含任何违反分区约束的行。同样,Postgres 12 改进了问题,例如 ATTACH 不会阻塞并发 INSERTs(和 SELECT/UPDATE/DELETE)。

为避免父表被长时间锁定以进行此验证检查,您可以在运行ATTACH 命令之前在要附加的表上添加与所需分区约束匹配的检查约束。有了检查约束,Postgres 可以跳过昂贵的ATTACH 验证步骤,因为分区约束已经有效,因为检查约束是有效的。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-05-19
    • 1970-01-01
    • 1970-01-01
    • 2016-12-09
    相关资源
    最近更新 更多