我有一个 JAVA 应用程序,可以使用任何供应商的 SQL 数据库。现在我们已经测试了 Vertica 和 PostgreSQL。我想从数据库中的一个表中导出所有数据,然后将其导入到应用程序的不同实例中。数据库的大小非常大,因此其中有很多行。导出和导入过程必须从 java 代码内部完成。
到目前为止我们尝试过的是:
- 导出:我们通过 JDBC 读取整个表 (
select * from
),然后将其转储到包含所需所有插入的 SQL 文件。 - 导入:包含数千个 INSERTS 的文件通过 JDBC 在目标数据库中执行。
这不是一个有效的过程。首先,select * from
部分由于其大小而给我们带来了问题,其次,如果一个接一个地插入,则执行大量操作会给我们在 Vertica 中带来问题 ( https://forum.vertica.com/discussion/235201/vjdbc-5065-error-too-many-ros-containers-exist-for-the-following-projections )
什么是更有效的方法来做到这一点?是否有任何工具可以帮助完成该过程,或者没有“优雅”的解决方案?
最佳答案
为什么不通过批处理(为了性能)和分块(以避免错误并提供失败后开始的检查点)一步完成导出/导入。
在大多数情况下,数据库支持具有多个值的 INSERT
查询,例如:
INSERT INTO table_a (col_a, col_b, ...) VALUES
(val_a, val_b, ...),
(val_a, val_b, ...),
(val_a, val_b, ...),
...
您生成到单个此类 INSERT
语句中的行数就是您的 block 大小,这可能需要针对特定目标数据库进行调整(大到足以加快速度,但又小到足以使 block 不超过某些数据库限制并创建失败)。
正如已经提出的,每个 block 都应该在事务中执行,并且您的应用程序应该记住最后成功执行的 block ,以防发生错误,以便它可以继续 em> 下次运行时。
对于 block 本身,您确实应该使用 LIMIT OFFSET .
这样,您可以随时重复任何 block ,每个 block 本身都是原子的,并且它的性能应该比单行语句好得多。
关于java - 如何使用 JDBC 高效导出/导入数据库数据,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55413399/