JdbcTemplate 执行与更新
您可以使用 JdbcTemplate 的 execute()方法执行 SQL 陈述,例如:
jdbcTemplate.execute("CREATE TABLE USER (user_id integer, name varchar(100))");
如果是 UPDATE 或 INSERT,您可以使用 update()方法,update()方法有数个重载(Overload)版本, 例如 接受实作 org.springframework.jdbc.core.PreparedStatementCreator 介面的 物件, PreparedStatementCreator 介面的定义如下:
package org.springframework.jdbc.core;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
public interface PreparedStatementCreator {
PreparedStatement createPreparedStatement(Connection con) throws SQLException;
}
例如您可以将 使用 JdbcTemplate 中UserDAO的insert()方法改写如下:
...
public void insert(User user) {
final String name = user.getName();
final int age = user.getAge().intValue();
jdbcTemplate.update(
new PreparedStatementCreator() {
public PreparedStatement createPreparedStatement( Connection con) throws SQLException {
String sql ="INSERT INTO user (name,age) VALUES(?,?)";
PreparedStatement ps =con.prepareStatement(sql);
ps.setString(1, name); ps.setInt(2, age); return ps;
}
...
}
});
在这个例子 中,可以使 用 PreparedStatement 预先编译 SQL , JdbcTemplate 上实现了 Template‐callback 机制,在执行 JDBC 的流程中,必要时会呼叫 callback 方法。 与 PreparedStatementCreator 互补的介面是 org.springframework.jdbc.core.PreparedStatementSetter 介面:
package org.springframework.jdbc.core;
import java.sql.PreparedStatement;
import java.sql.SQLException;
public interface PreparedStatementSetter {
void setValues(PreparedStatement ps) throws SQLException;
}
例如您可以将 使用 JdbcTemplate 中UserDAO的insert()方法改写如下:
...
public void insert(User user) {
final String name = user.getName();
final int age = user.getAge().intValue();
jdbcTemplate.update("INSERT INTO user (name,age) VALUES(?,?)", new PreparedStatementSetter() {
public void setValues(PreparedStatement ps)
throws SQLException {
ps.setString(1, name);
ps.setInt(2, age);
}
...
}
});
JdbcTemplate 会自动建立 PreparedStatementCreator 的实例,以提供传递给 setValues() 方法 的 PreparedStatement物件。 您也可以直接提供SQL,就如 使用 JdbcTemplate 中所示范的UserDAO中的insert()方法:
...
public void insert(User user) { String name = user.getName();
int age = user.getAge().intValue();
jdbcTemplate.update( "INSERT INTO user (name,age) " + "VALUES('" + name + "'," + age + ")");
}
...
在直接下SQL语句时,也可以使用"?"作为占位字元,并使用物件阵列作为引数传递给JdbcTemplate 的update()方法,例如改写 使用 JdbcTemplate 中所示范的UserDAO中的insert()方法:
...
public void insert(User user) {
jdbcTemplate.update( "INSERT INTO user (name, age) VALUES(?,?)",
new Object[] {user.getName(), user.getAge()});
}
...
JdbcTemplate 会自动建立 PreparedStatementCreator 与 PreparedStatementSetter 的实例,然而这 些细节您不用理会,您只要提供 SQL 与引数就好了。 如果需要批次处理时,可以实作 org.springframework.jdbc.core.BatchPreparedStatementSetter 介面:
package org.springframework.jdbc.core;
import java.sql.PreparedStatement;
import java.sql.SQLException;
public interface BatchPreparedStatementSetter {
void setValues(PreparedStatement ps,int i) throws SQLException;
int getBatchSize();
}
例如您可以在 使用 JdbcTemplate 中的IUserDAO介面及UserDAO类别上增加一个insertUsers()方 法的定义与实作,像是以下的内容:
...
public int[] insertUsers(final List users) {
String sql = "INSERT INTO user (name,age) VALUES(?,?)";
BatchPreparedStatementSetter setter = new BatchPreparedStatementSetter() {
public void setValues(PreparedStatement ps, int i)
throws SQLException {
User user = (User) users.get(i);
ps.setString(1, user.getName());
ps.setInt(2, user.getAge().intValue());
}
public int getBatchSize() {
return users.size();
}
};
return jdbcTemplate.batchUpdate(sql, setter);
}
...
如果您的 JDBC 驱动程式支援批次处理的话,则直接使用它的功能,如果不支援,则 Spring 会自 动一个一个处理更新以模拟批次处理。