Как получить возвращаемое значение из хранимой процедуры T-SQL в Java? - PullRequest
2 голосов
/ 02 ноября 2010

У меня есть хранимая процедура, которая добавляет объект в базу данных и возвращает сгенерированный идентификационный номер.

Для справки, его базовая структура выглядит примерно так:

ALTER PROCEDURE [dbo].[myProc] 
    @Name    nvarchar(50),
    @Creator nvarchar(50),
    @Text    nvarchar(200),
    @Lat     float,
    @Lon     float,
    @myID    int OUTPUT
AS
BEGIN
    SET NOCOUNT ON;

    INSERT INTO myTable --# blah blah blah
    SELECT @myID = scope_identity(); --# grab the auto-inc key from myTable
    INSERT INTO anotherTable --# blah blah blah
END

Я запустил это в SQL Server Management Studio и убедился, что он работает правильно.

Теперь я хочу вызвать эту хранимую процедуру из Java. Я написал этот код, чтобы сделать это:

CallableStatement cs = con.prepareCall("EXEC myProc "
  + "@Name = ?, @Creator = ?, @Text = ?, @Lat = ?, @Lon = ?, @myID = ? OUTPUT");
cs.setString(1, aString);
cs.setString(2, anotherString);
cs.setString(3, yetAnotherString);
cs.setFloat(4, aFloat);
cs.setFloat(5, anotherFloat);
cs.registerOutParameter(6, java.sql.Types.INTEGER);

cs.execute();

Но вызов execute() вызывает исключение:

java.sql.SQLException: [Microsoft][ODBC SQL Server Driver][SQL Server]Error converting data type nvarchar to int.

Что здесь не так? Почему он даже пытается преобразовать nvarchar в int? Я даже не пытаюсь получить возвращаемое значение через getInt() (это будет на следующей строке).

Что я пробовал:

  • Построение запроса путем манипулирования строками, чтобы проверить, может ли проблема быть во входных параметрах. Это же исключение. По крайней мере, это сужает проблему.
  • Изменение типа выходного параметра на Types.NVARCHAR, на всякий случай. Но это даже не поддерживается JdbcOdbcDriver, который я использую.
  • Возиться с синтаксисом вызова (я раньше не использовал SQL Server с Java). Всегда заканчивались ошибками синтаксиса. Это включало попытку сделать myID возвращаемым значением вместо выходного параметра.
  • Поиск в Google. Много. Завершается кучей бесполезных тем на форуме и EE "ответов".

Теперь я в тупике. Это действительно так сложно, или я просто упускаю очевидное?

Ответы [ 2 ]

2 голосов
/ 03 ноября 2010

Ваш код выглядит нормально. Единственное, что является неправильным, это то, что «float» в SQL Server отображает удвоение в Java. "реальный" в картах MS SQL, чтобы плавать в Java. Но это не создает проблемы.

Проблема в глючном ODBC Bridge. Вы должны использовать драйвер JDBC типа 4 для MS SQL. Если вы хотите использовать ODBC Bridge, вы можете проверить установку значения для 6-го параметра:

cs.setInt(6, 0);

Но я не знаю, будет ли это работать. Сообщение означает, что драйвер использует тип данных NVARCHAR для последнего параметра. Похоже, ODBC Bridge не передает тип с помощью registerOutParameter.

0 голосов
/ 03 ноября 2010

Невозможно проверить ваш код, поскольку у меня нет SQL Server, но вы можете попробовать изменить его на String, поскольку это эквивалент Java для NVARCHAR.

...