Vol*_*auf 14 postgresql alter-table postgresql-9.3
尝试向NOT NULL
具有 10 亿行的表添加约束。我无法承受超过几秒钟的表锁。有没有办法在alter table 语句期间防止全表扫描?我在列上创建了一个索引,希望它能被使用,但这似乎不起作用。可能是检查约束?其他选择?谢谢!
有没有办法在alter table 语句期间防止全表扫描?
目前没有支持的、安全的方式来使用 PostgreSQL 来做到这一点。
某种方式ALTER TABLE ... ADD CONSTRAINT ... CONCURRENTLY
会很好,但没有人实施它。与添加NOT VALID
仍然影响新行的约束的替代方案相同,然后您VALIDATE
稍后 - 这会很好,而且每个人都知道这是需要的,但没有人有时间或资金添加。
理论上,如果您知道它是真实有效的,您可以直接修改系统目录以添加约束。实际上,这通常不是一个好主意。
所以不,真的没有办法。
小智 9
一种可能的替代方法是使用 创建检查约束NOT VALID
,然后稍后验证检查约束。这种方法ACCESS EXCLUSIVE
只需要在创建约束的持续时间内持有锁,这应该是毫秒级的。该VALIDATE
命令将执行耗时的全表扫描以验证约束,但它持有限制性较小的SHARE UPDATE EXCLUSIVE
锁。
至于权衡,我一直找不到任何提到标准NOT NULL
约束和验证列不为空的检查约束之间的内部机制差异的文档。我记得挖掘了一个论坛帖子,其中没有潜在的性能差异,但丢失了链接,所以这是未经证实的。
ALTER TABLE table ADD CONSTRAINT table_value_not_null_check CHECK (value IS NOT NULL) NOT VALID;
ALTER TABLE table VALIDATE CONSTRAINT table_value_not_null_check;
Run Code Online (Sandbox Code Playgroud)
资料来源:
https://www.postgresql.org/docs/9.4/static/sql-altertable.html https://www.postgresql.org/docs/9.4/static/explicit-locking.html
归档时间: |
|
查看次数: |
5613 次 |
最近记录: |