I know it is poor form to report two things at once but the replication instructions are very similar and bugs may be similar.

I am using iBATIS from subversion updated Friday am.

I am interacting with my db solely through stored procedures.

Earlier, I had problems with iBATIS not realizing that my calls had altered the database and therefore not committing. To work around this, I set my transactionManager to commitRequired="true"
             <transactionManager type="JDBC" commitRequired="true">

Here is the signature of the Stored Proc. I am using MySql 5.1.12-beta.
CREATE PROCEDURE deleteDatasetByResearcherIdAndId(
   pResearcherId INT(11),
   pDatasetId INT(11)
)
DETERMINISTIC
MODIFIES SQL DATA
BEGIN
blah blah .....
END


However, I have found a case where iBATIS is not sending the commit and the call to the db is basically hanging waiting for the commit. To test this I have tested my call with three different iBATIS xml elements. I had trouble with two of the cases and have full details below. 1) using statement, I get an indefinite hang because no commit is ever sent by iBATIS
   2) using procedure I get a NullPointerException
   3) using a delete element, I got it to work


#1 using statement

<statement id="deleteDatasetByResearcherIdAndIdStatement" resultClass="Integer" parameterClass="Map">
   CALL deleteDatasetByResearcherIdAndId(
     #pResearcherId:NUMERIC#,
     #pDatasetId:NUMERIC#
   )
 </statement>

public static Integer deleteDatasetByResearcherIdAndIdStatement(int pResearcherId, int pDatasetId) {
   Map<String, Object> map = new HashMap<String, Object>();
   map.put("pResearcherId", pResearcherId);
   map.put("pDatasetId", pDatasetId);
return cast(sqlMapper.queryForObject("deleteDatasetByResearcherIdAndIdStatement", map));
 }

The MySQL log shows this:
                 240 Query     SET autocommit=1
                 240 Query     SET autocommit=0
240 Query CALL deleteDatasetByResearcherIdAndId( 1, 1 )
NOTE: NO COMMIT

#2 using Procedure

<procedure id="deleteDatasetByResearcherIdAndIdProcedure" resultClass="Integer" parameterClass="Map">
   CALL deleteDatasetByResearcherIdAndId(
     #pResearcherId:NUMERIC#,
     #pDatasetId:NUMERIC#
   )
 </procedure>

public static Integer deleteDatasetByResearcherIdAndIdProcedure(int pResearcherId, int pDatasetId) {
   Map<String, Object> map = new HashMap<String, Object>();
   map.put("pResearcherId", pResearcherId);
   map.put("pDatasetId", pDatasetId);
return cast(sqlMapper.queryForObject("deleteDatasetByResearcherIdAndIdProcedure", map));
 }

2006-11-21 18:33:48,381 DEBUG: queryForObject deleteDatasetByResearcherIdAndIdProcedure passing: {pDatasetId=1, pResearcherId=1}
2006-11-21 18:33:48,384 DEBUG: {conn-100003} Connection
2006-11-21 18:33:48,392 DEBUG: {conn-100003} Preparing Call: CALL deleteDatasetByResearcherIdAndId( ?, ? )
2006-11-21 18:33:48,428 ERROR: Error calling Connection.prepareCall:
java.lang.NullPointerException
at com.mysql.jdbc.StringUtils.indexOfIgnoreCaseRespectQuotes(StringUtils.java:959) com.ibatis.common.jdbc.exception.NestedSQLException: at com.mysql.jdbc.DatabaseMetaData.getCallStmtParameterTypes(DatabaseMetaData.java:1296) --- The error occurred in org/epistasis/db/geneDataset/GeneDataset.xml. at com.mysql.jdbc.DatabaseMetaData.getProcedureColumns(DatabaseMetaData.java:3670) --- The error occurred while executing query procedure. at com.mysql.jdbc.CallableStatement.determineParameterTypes(CallableStatement.java:702) --- Check the CALL deleteDatasetByResearcherIdAndId( ?, ? ). --- Check the SQL Statement (preparation failed). at com.mysql.jdbc.CallableStatement.<init>(CallableStatement.java:513)
--- Cause: java.lang.NullPointerException
at com.mysql.jdbc.Connection.parseCallableStatement(Connection.java:4422)
Caused by: java.lang.NullPointerException
       at com.mysql.jdbc.Connection.prepareCall(Connection.java:4496)
       at com.mysql.jdbc.Connection.prepareCall(Connection.java:4470)
at com.ibatis.sqlmap.engine.mapping.statement.GeneralStatement.executeQueryWithCallback(GeneralStatement.java:188) at org.apache.commons.dbcp.DelegatingConnection.prepareCall(DelegatingConnection.java:212) at org.apache.commons.dbcp.PoolingDataSource$PoolGuardConnectionWrapper.prepareCall(PoolingDataSource.java:268) at com.ibatis.sqlmap.engine.mapping.statement.GeneralStatement.executeQueryForObject(GeneralStatement.java:104)
       at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at com.ibatis.sqlmap.engine.impl.SqlMapExecutorDelegate.queryForObject(SqlMapExecutorDelegate.java:566) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) at com.ibatis.sqlmap.engine.impl.SqlMapExecutorDelegate.queryForObject(SqlMapExecutorDelegate.java:541) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
       at java.lang.reflect.Method.invoke(Method.java:585)
at com.ibatis.sqlmap.engine.impl.SqlMapSessionImpl.queryForObject(SqlMapSessionImpl.java:106) at com.ibatis.sqlmap.engine.impl.SqlMapClientImpl.queryForObject(SqlMapClientImpl.java:83) at com.ibatis.common.jdbc.logging.ConnectionLogProxy.invoke(ConnectionLogProxy.java:60)
       at $Proxy0.prepareCall(Unknown Source)
at com.ibatis.sqlmap.engine.execution.SqlExecutor.prepareCall(SqlExecutor.java:500) at com.ibatis.sqlmap.engine.execution.SqlExecutor.executeQueryProcedure(SqlExecutor.java:260) at com.ibatis.sqlmap.engine.mapping.statement.ProcedureStatement.sqlExecuteQuery(ProcedureStatement.java:34) at org.epistasis.db.SqlMapClientWrapper.queryForObject(SqlMapClientWrapper.java:46) at com.ibatis.sqlmap.engine.mapping.statement.GeneralStatement.executeQueryWithCallback(GeneralStatement.java:173) at org.epistasis.db.geneDataset.GeneDatasetDbAccess.deleteDatasetByResearcherIdAndIdProcedure(GeneDatasetDbAccess.java:84) at com.ibatis.sqlmap.engine.mapping.statement.GeneralStatement.executeQueryForObject(GeneralStatement.java:104) at org.epistasis.db.geneDataset.GeneDatasetDbAccess.main(GeneDatasetDbAccess.java:99) at com.ibatis.sqlmap.engine.impl.SqlMapExecutorDelegate.queryForObject(SqlMapExecutorDelegate.java:566)

#3 using Delete worked!
 <delete id="deleteDatasetByResearcherIdAndId"  parameterClass="Map">
   CALL deleteDatasetByResearcherIdAndId(
     #pResearcherId:NUMERIC#,
     #pDatasetId:NUMERIC#
   )
 </delete>

public static int deleteDatasetByResearcherIdAndId(int pResearcherId, int pDatasetId) {
   Map<String, Object> map = new HashMap<String, Object>();
   map.put("pResearcherId", pResearcherId);
   map.put("pDatasetId", pDatasetId);
   return sqlMapper.delete("deleteDatasetByResearcherIdAndId", map);
 }

--
Peter Andrews
Software Engineer
Dartmouth Medical School
Computational Genetics
Rubin 707
(603) 653-3598
[EMAIL PROTECTED]

Reply via email to