首页 > 解决方案 > SimpleJdbcCall 存储过程调用在第一次调用后失败

问题描述

我正在使用 JdbcTemplate 调用 as400 中的存储过程。我知道架构和程序存在,并且我使用了正确的拼写等。

应用程序第一次启动调用按预期工作并且没有错误。后续调用失败并出现以下错误:

 org.springframework.jdbc.BadSqlGrammarException: CallableStatementCallback; bad SQL grammar [{call PGM999.STOREDPROCNAME(?, ?, ?, ?, ?, ?, ?)}]; nested exception is com.ibm.as400.access.AS400JDBCSQLSyntaxErrorException: [SQL0204] NEWSP in RGRPGM type *N not found.

这是一个@Service类中的一些相关代码片段:

private ConcurrentMap<String, SimpleJdbcCall> storedProcedureCallsMap = new ConcurrentHashMap<String, SimpleJdbcCall>();

public Map<String, Object> executeStoredProcedure(String procedureName, MapSqlParameterSource paramSource, String libraryName) {
    return executeStoredProcedureCall(procedureName, paramSource, createCallForStoredProcedure(procedureName, libraryName));
}

private CallCreator createCallForStoredProcedure(String procedureName, String libraryName) {
    return new CallCreator() {
        @Override
        public SimpleJdbcCall createCall() {
            return new SimpleJdbcCall(as400JdbcTemplate).withSchemaName(libraryName).withProcedureName(procedureName);
        }
    };
}
 //
  SimpleJdbcCall call = storedProcedureCallsMap.get(procedureName);

  call = callCreator.createCall();
  call.compile();

  Map<String, Object> returnMap = call.execute(paramsSource);

奇怪的是,当我调用以下之一时:或者Connection.commit()它每次都有效,但是,在所有这些中,它都会锁定线程池中的连接,甚至调用也不会关闭它们,它们会保持活动状态,直到没有空闲连接留给使用,它锁定了整个事情。Connection.endRequest()Connection.setAutoCommit(true)Connection.close()

因此,我要么需要解决第一个问题,每次都可以正常工作而不告诉它提交等,要么是我调用其中一个但成功强制它释放连接的第二个问题。

标签: javaibm-midrangejdbctemplatesimplejdbccall

解决方案


事实证明,有问题的存储过程正在调用另一个尚未复制到主过程正在使用的模式的存储过程。我仍然不知道为什么它第一次会起作用,或者当我告诉它提交时,它每次都会起作用。无论哪种方式,将丢失的过程复制到相同的模式似乎都可以解决问题。


推荐阅读