我正在尝试使用预处理语句executebatch将多行插入Oracle表中...我得到了java.sql.BatchUpdateException: invalid argument(s) in call
异常并且我的连接没有问题..它在所有方面都有效其他功能......
我在网上搜索并在java.sql.SQLException
的通话中找到了无效的参数,但BatchUpdateException
没有。
任何帮助都会非常感激。
public void insert(List<Employee> str, Connection con) throws SQLException {
String sql = "insert into tbl_list(e_name,e_id) values (?,?)";
PreparedStatement ps = con.prepareStatement(sql);
con.setAutoCommit(false);
for (int i = 1; i <= str.size(); i++) {
ps.setString(1, str.get(i - 1).getName());
ps.setString(2, str.get(i - 1).getId());
ps.addBatch();
}
ps.executeBatch();
ps.close();
con.close();
}
堆栈跟踪是:
2017年5月16日下午2:34:40 org.apache.catalina.core.StandardWrapperValve在上下文中调用SEVERE:servlet [spring]的Servlet.service(),路径[/ insert]引发异常[请求处理失败;嵌套异常是java.sql.BatchUpdateException:调用中的无效参数有根本原因java.sql.BatchUpdateException:在oracle.jdbc.driver的oracle.jdbc.driver.OraclePreparedStatement.executeBatch(OraclePreparedStatement.java:10345)调用时无效的参数.OracleStatementWrapper.executeBatch(OracleStatementWrapper.java:230)org.apache.tomcat.dbcp.dbcp.DelegatingStatement.executeBatch(DelegatingStatement.java:297)atg.apache.tomcat.dbcp.dbcp.DelegatingStatement.executeBatch(DelegatingStatement.java) :297)at dao.insert.preparedInsert(insert.java:322)
insert.java:322是ps.executeBatch();
答案 0 :(得分:1)
您的查询最后包含(?,?,?,?,?,)
5?和拼写错误,
,但您只为查询设置了2个参数:
ps.setString(1, str.get(i-1).getName());
ps.setString(2,str.get(i-1).getId());
相反,您必须更正您的查询,并且在评论中提及@Berger时,您必须在查询中指定列名称:
String sql = "insert into tbl_list(col_name1, col_name2) values (?,?)";
或者你必须设置正确的参数数量。
您还必须使用con.setAutoCommit(false);
和con.commit();
,如下所示:
con.setAutoCommit(false); // disabling autoCommit is recommend for batching
PreparedStatement ps = con.prepareStatement(sql);
for (int i = 1; i <= str.size(); i++) {
ps.setString(1, str.get(i - 1).getName());
ps.setString(2, str.get(i - 1).getId());
ps.addBatch();
}
ps.executeBatch();
con.commit();//commit statements to apply changes
答案 1 :(得分:1)
Well I would recommend specifiying column names in the query String
too, but I think you problem lies in setting the arguuments.
And more specifically the problem is with ps.addBatch()
call, in fact you better use Statement
and its .addBatch(String sql) method accepts an SQL String
so i will take in consideration the updated SQL query in each iteration, so just make sure to pass it in ps.addBatch(sql)
.
And why would your for
loop start from 1
and then use
.get(i-1)
, if it can simply start from 0
?
Just update your code accordingly:
public void insert(List < Employee > str, Connection con) throws SQLException {
String sql = "insert into tbl_list(e_name,e_id) values (?,?)";
Statement ps = con.createStatement();
for (int i = 0; i <= str.size(); i++) {
ps.setString(1, str.get(i).getName());
ps.setString(2, str.get(i).getId());
ps.addBatch(sql); //Note the sql String here
}
ps.executeBatch();
ps.close();
con.close();
}
And if the problem persists with setting query arguments, why don't you just create the query in the loop itself and change it dynamically?
Here's what I suggest here:
for (int i = 0; i <= str.size(); i++) {
String sql = "insert into tbl_list(e_name,e_id) values ('"+str.get(i).getName()+"','"+str.get(i).getId()+"')";
ps.addBatch(sql);
}
You can take a look at this Batch Insert In Java – JDBC tutorial for further reading and for full options.
答案 2 :(得分:0)
检查此循环。
这里,在i = 0的情况下,取出(0-1)为-1。
我们知道List提供了基于0的索引,所以你的str.get(..)
应该从0开始,而不是从-1开始
试试这个
public void insert(List<Employee> str, Connection con) throws SQLException {
String sql = "insert into tbl_list values (?,?)";
PreparedStatement ps = con.prepareStatement(sql);
for (Employee e:str) {
ps.setString(1, e.getName());
ps.setLong(2, e.getId());
ps.addBatch();
}
ps.executeBatch();
ps.close();
con.close();
}
堆栈跟踪是:
`2017年5月16日下午2:34:40 org.apache.catalina.core.StandardWrapperValve调用 严重:servlet [spring]的Servlet.service()在路径[/ insert]的上下文中引发异常[请求处理失败;嵌套异常是java.sql.BatchUpdateException:调用中的无效参数有根本原因 java.sql.BatchUpdateException:调用中的参数无效 at oracle.jdbc.driver.OraclePreparedStatement.executeBatch(OraclePreparedStatement.java:10345) at oracle.jdbc.driver.OracleStatementWrapper.executeBatch(OracleStatementWrapper.java:230) at org.apache.tomcat.dbcp.dbcp.DelegatingStatement.executeBatch(DelegatingStatement.java:297) at org.apache.tomcat.dbcp.dbcp.DelegatingStatement.executeBatch(DelegatingStatement.java:297) 在dao.insert.preparedInsert(insert.java:322)
insert.java:322是ps.executeBatch();`