使用jdbc插入多个表
我正在尝试使用 JDBC 插入多个表。因为它必须很快,所以我想使用 PreparedStatement
和 executeBatch
方法。表通过外键关系组合。
第一个想法是使用
getGenerateKeys()
但对于某些 JDBC 驱动程序来说这会失败。例如 PostgreSQL。第二个想法是使用 SQL-currval(...) 函数。但是必须为一个语句调用执行批处理,而为另一个语句调用执行批处理会使所有键具有相同的值。所以这个方法也失败了。
JDBC 不接受分号分隔插入。
我怎样才能实现这个目标?
I am trying to use JDBC to insert into multiple tables. Because it has to be fast I want to use PreparedStatement
and the executeBatch
method. Tables are combinded by a foreign key relationship.
First idea was to use
getGeneratedKeys()
but this fails with some JDBC drivers. E.g. PostgreSQL.Second idea was to use the SQL-currval(...)-function. But having to call execute batch for one statement and the for the other makes all keys the same value. So this method also fails.
JDBC doesn't accept semicolon separeted inserts.
How can I achieve this?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
您似乎主要使用 PostgreSQL。最好知道从 PostgreSQL JDBC 驱动程序版本 8.4-701 开始
PreparedStatement#getGenerateKeys ()
功能齐全。您只需按如下方式准备语句即可使其返回密钥:
因此,如有必要,请升级您的驱动程序并修复准备语句的方式。顺便说一句,这也适用于许多其他 JDBC 驱动程序。
一种完全不同的替代方案是完全放弃普通的 JDBC,而向上一个抽象层并深入研究“优秀的”Hibernate 或现代 JPA。他们提供了一种纯面向对象的方法,用 Java 处理数据库实体,无需摆弄生成的键等。这一切都是在幕后透明处理的,并且它们支持非常广泛的数据库方言。
You seem to be mainly using PostgreSQL. It may be good to know that since PostgreSQL JDBC driver version 8.4-701 the
PreparedStatement#getGeneratedKeys()
is fully functional.You only need to prepare the statement as follows to make it to return the keys:
So, upgrade if necessary your driver and fix the way how you prepare the statement. This applies by the way also on many other JDBC drivers.
A completely different alternative is to drop plain JDBC altogether and go one abstraction layer up and dive in "good 'ol" Hibernate or the modern JPA. They offers a pure object oriented approach of database entity handling in Java without the need to fiddle with generated keys and like. It's all handled under the covers transparently and they supports a very wide range of DB dialects.
如果代码必须快速运行,那么您应该尝试编写一个存储过程/函数,它将接受将插入到表中的值数组。
这是一个示例。
If the code has to run fast then you should try writing a stored procedure/function which will accept arrays of values which will be inserted in the tables.
Here's an example.
好吧,这是我自己的答案。
只要供应商无法正确实现 getGenerateKeys() 函数,您就需要和数据库特定的后备选项。
如果您需要不受欢迎的数据库的后备,则会使代码变得非常丑陋。
这是我针对 Postgres 9.0 的解决方法:
"SELECT nextval('public.\"table_column_seq\"') FROMgenerate_series(1,"+pollsize+")");
浪费了一整天的时间,然后我得到的只是一个丑陋的解决方案。 JDBC 应该检查应用程序启动时驱动程序是否确实符合其期望,否则会抛出一些不可恢复的邪恶 YouVeGotaF**ckedUpDriverException。
Okay here's my own answer.
So long the vendors can't implement the getGeneratedKeys() function correctly you need and database specific fallback option.
Makes the code very ugly, if you need fallbacks for unsported databases.
Here my workaround for Postgres 9.0:
"SELECT nextval('public.\"table_column_seq\"') FROM generate_series(1,"+pollsize+")");
Wasted a whole bloody day on that, and then all I get is an ugly solution. JDBC should check on app-startup if the driver really holds up to its expectation and otherwise throw some unrecoverable wicked YouVeGotaF**ckedUpDriverException.