【问题标题】:How to import *huge* chunks of data to PostgreSQL?如何将 *huge* 数据块导入 PostgreSQL?
【发布时间】:2011-03-27 03:05:38
【问题描述】:

我有一个如下所示的数据结构:

Model Place
    primary key "id"

    foreign key "parent" -> Place
    foreign key "neighbor" -> Place (symmetryc)
    foreign key "belongtos" -> Place (asymmetric)

    a bunch of scalar fields ...

模型表中有超过 500 万行,我需要在两个外键表中的每一个中插入 ~5000 万 行。我有SQL 看起来像这样的文件:

INSERT INTO place_belongtos (from_place_id, to_place_id) VALUES (123, 456);

每个大约 7 Gb。问题是,当我执行psql < belongtos.sql 时,在我的 AMD Turion64x2 CPU 上导入 ~400 万 行大约需要 12 小时。操作系统是 Gentoo ~amd64,PostgreSQL 是 8.4 版,本地编译。数据目录是绑定挂载,位于我的第二个扩展分区 (ext4),我认为这不是瓶颈。

我怀疑插入外键关系需要很长时间,因为psql 检查每一行的键约束,这可能会增加一些不必要的开销,因为我确信数据是有效的。有没有办法加快导入,即暂时禁用约束检查?

【问题讨论】:

  • 是的,但我认为它只有 8.4+ 嗯必须查一下....

标签: sql database postgresql performance


【解决方案1】:
  1. 确保两个外键约束都是DEFERRABLE
  2. 使用COPY 加载您的数据
  3. 如果您不能使用 COPY,请使用 prepared statement 作为 INSERT。
  4. 适当的配置设置也会有所帮助,请检查WAL 设置。

【讨论】:

  • +1 for COPY,对我遇到的那些定期插入大量数据的数据库产生了巨大的影响......
  • 我已经使用 DEFERRABLE。 COPY 是我一直在寻找的东西,谢谢!
  • 使用 deferable 是一回事,真正使用这个选项是另一回事:INITIALLY DEFERRED 或 SET CONSTRAINTS ALL DEFERRED;
  • 删除索引、约束和触发器,然后在导入完成后重建它们甚至可能是有意义的。
【解决方案2】:

答案是肯定的...Depesz wrote an article here on deferrable uniqueness。不幸的是,它似乎是 9.0 的功能。

嗯...也许那篇文章不适用于您的情况?似乎我们已经能够set constraints to deferred 有一段时间了...我猜独特是一种独特的情况(双关语)。

【讨论】:

  • 外键在旧版本中已经可以延期了,没问题。
  • Depesz 的文章描述了在 9.0 之前不可延迟的可延迟 unique 约束(例如主键),例如运行 UPDATE id = id + 1 (其中 id 是 PK 列) 常规 FK 约束“总是”可以推迟。将约束设置为可延迟不会阻止检查,它只会将检查延迟到事务结束(即执行提交时)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-10-08
  • 2011-03-25
  • 2017-07-17
  • 2021-10-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多