根据 Spring 3.2 文档(http://static.springsource.org/spring/docs/3.2. x/spring-framework-reference/html/jdbc.html ):
public class JdbcActorDao implements ActorDao {
private JdbcTemplate jdbcTemplate;
private SimpleJdbcCall procReadActor;
public void setDataSource(DataSource dataSource) {
this.jdbcTemplate = new JdbcTemplate(dataSource);
this.procReadActor =
new SimpleJdbcCall(dataSource)
.withProcedureName("read_actor");
}
public Actor readActor(Long id) {
SqlParameterSource in = new MapSqlParameterSource()
.addValue("in_id", id);
Map out = procReadActor.execute(in);
Actor actor = new Actor();
actor.setId(id);
actor.setFirstName((String) out.get("out_first_name"));
actor.setLastName((String) out.get("out_last_name"));
actor.setBirthDate((Date) out.get("out_birth_date"));
return actor;
}
// ... additional methods
}
我的实现是这样的:
@Repository
public class ObjectDao {
private JdbcTemplate jdbcTemplate;
@Value("${db.sp.getObject}")
private String spName;
private SimpleJdbcCall jdbcCall;
@Autowired
public void setDataSource(DataSource dataSource) {
this.jdbcTemplate = new JdbcTemplate(dataSource);
this.jdbcCall=
new SimpleJdbcCall(dataSource)
.withProcedureName(spName);
}
public SQLXML getDbObjectById(Integer id) {
SqlParameterSource in = new MapSqlParameterSource()
.addValue("objectId", id, Types.INTEGER);
Map<String, Object> out = jdbcCall.execute(in);
return (SQLXML) out.get("OutputXML");
}
}
我已经用其他数据库事务测试了连接参数,这些都成功了,但是当尝试读取使用 XML 变量的输出参数时,我会看到如下所示的 BadSqlGrammarException
EXECEPTION
org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:948)
org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:827)
javax.servlet.http.HttpServlet.service(HttpServlet.java:621)
org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:812)
javax.servlet.http.HttpServlet.service(HttpServlet.java:722)
ROOT CAUSE
org.springframework.jdbc.BadSqlGrammarException: CallableStatementCallback; bad SQL grammar [{call spXML_Wrapper(?, ?, ?)}]; nested exception is c om .microsoft.sqlserver.jdbc.SQLServerException: Implicit conversion from data type xml to nvarchar(max) is not allowed. Use the CONVERT function to run this query.
org.springframework.jdbc.support.SQLStateSQLExceptionTranslator.doTranslate(SQLStateSQLExceptionTranslator.java:98)
org.springframework.jdbc.support.AbstractFallbackSQLExceptionTranslator.translate(AbstractFallbackSQLExceptionTranslator.java:72)
org.springframework.jdbc.support.AbstractFallbackSQLExceptionTranslator.translate(AbstractFallbackSQLExceptionTranslator.java:80)
org.springframework.jdbc.support.AbstractFallbackSQLExceptionTranslator.translate(AbstractFallbackSQLExceptionTranslator.java:80)
org.springframework.jdbc.core.JdbcTemplate.execute(JdbcTemplate.java:1036)
org.springframework.jdbc.core.JdbcTemplate.call(JdbcTemplate.java:1070)
org.springframework.jdbc.core.simple.AbstractJdbcCall.executeCallInternal(AbstractJdbcCall.java:387)
org.springframework.jdbc.core.simple.AbstractJdbcCall.doExecute(AbstractJdbcCall.java:350)
org.springframework.jdbc.core.simple.SimpleJdbcCall.execute(SimpleJdbcCall.java:181)
com.test.dao.ObjectDao.getDbObjectById(InvoiceDaoImpl.java:59)
........
ROOT CAUSE
com.microsoft.sqlserver.jdbc.SQLServerException: Implicit conversion from data type xml to nvarchar(max) is not allowed. Use the CONVERT function to run this query.
com.microsoft.sqlserver.jdbc.SQLServerException.makeFromDatabaseError(SQLServerException.java:216)
com.microsoft.sqlserver.jdbc.SQLServerStatement.getNextResult(SQLServerStatement.java:1515)
com.microsoft.sqlserver.jdbc.SQLServerPreparedStatement.doExecutePreparedStatement(SQLServerPreparedStatement.java:404)
com.microsoft.sqlserver.jdbc.SQLServerPreparedStatement$PrepStmtExecCmd.doExecute(SQLServerPreparedStatement.java:350)
com.microsoft.sqlserver.jdbc.TDSCommand.execute(IOBuffer.java:5696)
com.microsoft.sqlserver.jdbc.SQLServerConnection.executeCommand(SQLServerConnection.java:1715)
com.microsoft.sqlserver.jdbc.SQLServerStatement.executeCommand(SQLServerStatement.java:180)
com.microsoft.sqlserver.jdbc.SQLServerStatement.executeStatement(SQLServerStatement.java:155)
com.microsoft.sqlserver.jdbc.SQLServerPreparedStatement.execute(SQLServerPreparedStatement.java:332)
org.apache.commons.dbcp.DelegatingPreparedStatement.execute(DelegatingPreparedStatement.java:172)
org.apache.commons.dbcp.DelegatingPreparedStatement.execute(DelegatingPreparedStatement.java:172)
org.springframework.jdbc.core.JdbcTemplate$6.doInCallableStatement(JdbcTemplate.java:1072)
org.springframework.jdbc.core.JdbcTemplate$6.doInCallableStatement(JdbcTemplate.java:1070)
org.springframework.jdbc.core.JdbcTemplate.execute(JdbcTemplate.java:1020)
org.springframework.jdbc.core.JdbcTemplate.call(JdbcTemplate.java:1070)
org.springframework.jdbc.core.simple.AbstractJdbcCall.executeCallInternal(AbstractJdbcCall.java:387)
org.springframework.jdbc.core.simple.AbstractJdbcCall.doExecute(AbstractJdbcCall.java:350)
org.springframework.jdbc.core.simple.SimpleJdbcCall.execute(SimpleJdbcCall.java:181)
com.test.dao.ObjectDao.getDbObjectById(InvoiceDaoImpl.java:59)
.......
我已经检查过存储过程本身是否符合要求 - 执行得很好。是否有人对此类错误有任何经验或有任何替代建议来使用 Spring 框架从存储过程中读取 XML 输出?
其他信息:
春天 3.2
雄猫 7.0
适用于 SQL Server 的 Microsoft JDBC 驱动程序 4.0
谢谢你的帮助