SimpleJdbcCall — ошибка при выполнении процедуры оракула

Я пытаюсь выполнить процедуру из метода SimpleJdbcCall's execute() (т.е. выполнение хранимой процедуры в Spring), но это дает ошибку, потому что у меня есть двойной кавычки в имени моего пакета - "_test_package". Ошибка говорит о том, что процедура должна быть объявлена, даже если она существует.

У меня есть следующий пакет с процедурой в Oracle -


Package Spec :-
CREATE OR REPLACE package GOVINDS."_test_package" is

    procedure createHelloMessage(namemsg in out VARCHAR2);

end "_test_package";

Package Body :-
CREATE OR REPLACE package body GOVINDS."_test_package" is

    procedure createHelloMessage(namemsg in out VARCHAR2) is
    begin
        namemsg := 'Hello '|| namemsg;
    end createHelloMessage;

end "_test_package";

Я пытаюсь выполнить его из Spring SimpleJdbcCall, как показано ниже, но выдает ошибку PLS-00201: должен быть объявлен идентификатор GOVINDS._TEST_PACKAGE.

SimpleJdbcCall simpleJdbcCallObject =
    new SimpleJdbcCall(jdbcTemplate).withSchemaName("GOVINDS").withCatalogName("\"_test_package\"").withProcedureName("createHelloMessage")
        .withoutProcedureColumnMetaDataAccess()
        .withNamedBinding()
        .declareParameters(new SqlParameter("namemsg", OracleTypes.VARCHAR));

SqlParameterSource in = new MapSqlParameterSource().addValue("namemsg", "Jim", OracleTypes.VARCHAR);

Map<String, Object> out = simpleJdbcCallObject.execute(in);

Ошибка стека:

org.springframework.jdbc.BadSqlGrammarException: CallableStatementCallback; bad SQL grammar [{call GOVINDS."_TEST_PACKAGE".CREATEHELLOMESSAGE(namemsg => ?)}]; nested exception is java.sql.SQLException: ORA-06550: line 1, column 7:
PLS-00201: identifier 'GOVINDS._TEST_PACKAGE' must be declared
ORA-06550: line 1, column 7:
PL/SQL: Statement ignored

at org.springframework.jdbc.support.SQLErrorCodeSQLExceptionTranslator.doTranslate(SQLErrorCodeSQLExceptionTranslator.java:231) ~[spring-jdbc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.jdbc.support.AbstractFallbackSQLExceptionTranslator.translate(AbstractFallbackSQLExceptionTranslator.java:73) ~[spring-jdbc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.jdbc.core.JdbcTemplate.execute(JdbcTemplate.java:1094) ~[spring-jdbc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.jdbc.core.JdbcTemplate.call(JdbcTemplate.java:1130) ~[spring-jdbc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.jdbc.core.simple.AbstractJdbcCall.executeCallInternal(AbstractJdbcCall.java:405) ~[spring-jdbc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.jdbc.core.simple.AbstractJdbcCall.doExecute(AbstractJdbcCall.java:365) ~[spring-jdbc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.jdbc.core.simple.SimpleJdbcCall.execute(SimpleJdbcCall.java:198) ~[spring-jdbc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
...
...
Caused by: java.sql.SQLException: ORA-06550: line 1, column 7:
PLS-00201: identifier 'GOVINDS._TEST_PACKAGE' must be declared
ORA-06550: line 1, column 7:
PL/SQL: Statement ignored

at oracle.jdbc.driver.T4CTTIoer.processError(T4CTTIoer.java:445) ~[ojdbc6-11.2.0.3.jar:11.2.0.3.0]
at oracle.jdbc.driver.T4CTTIoer.processError(T4CTTIoer.java:396) ~[ojdbc6-11.2.0.3.jar:11.2.0.3.0]
at oracle.jdbc.driver.T4C8Oall.processError(T4C8Oall.java:879) ~[ojdbc6-11.2.0.3.jar:11.2.0.3.0]
at oracle.jdbc.driver.T4CTTIfun.receive(T4CTTIfun.java:450) ~[ojdbc6-11.2.0.3.jar:11.2.0.3.0]
at oracle.jdbc.driver.T4CTTIfun.doRPC(T4CTTIfun.java:192) ~[ojdbc6-11.2.0.3.jar:11.2.0.3.0]
at oracle.jdbc.driver.T4C8Oall.doOALL(T4C8Oall.java:531) ~[ojdbc6-11.2.0.3.jar:11.2.0.3.0]
at oracle.jdbc.driver.T4CCallableStatement.doOall8(T4CCallableStatement.java:204) ~[ojdbc6-11.2.0.3.jar:11.2.0.3.0]
at oracle.jdbc.driver.T4CCallableStatement.executeForRows(T4CCallableStatement.java:1041) ~[ojdbc6-11.2.0.3.jar:11.2.0.3.0]
at oracle.jdbc.driver.OracleStatement.doExecuteWithTimeout(OracleStatement.java:1329) ~[ojdbc6-11.2.0.3.jar:11.2.0.3.0]

Если я попытаюсь выполнить с помощью jdbcTemplate.call(), он будет работать нормально. Я предпочитаю SimpleJdbcCall.execute(), потому что для согласованности я не хочу менять код 95-97%.


person GovindS    schedule 17.06.2016    source источник


Ответы (2)


Это связано с тем, что строка с двойными кавычками чувствительна к регистру, так как Spring JDBC преобразует вашу строку в верхний регистр, однако ваше фактическое имя процедуры указано в маленьком регистре. Попробуйте изменить имя процедуры на верхний регистр, ваш код должен работать.

person Chetan    schedule 21.06.2016

Проблема заключается в том, что spring jdbc преобразует строку вызывающего оператора в верхний регистр (даже имя объекта указывается в двойных кавычках), и если имя пакета, указанное в двойных кавычках, чувствительно к регистру.

Решением может быть создание синонима для имени пакета.

create or replace synonym GOVINDS.test_package for GOVINDS."_test_package";
person GovindS    schedule 07.03.2017