Calling stored procedure with named JDBC parameters raises exception

独自空忆成欢 提交于 2020-05-28 09:55:55

问题


package com.brookfieldres.operations;

import java.sql.CallableStatement;
import java.sql.Connection;
import java.sql.Date;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.Properties;
import java.util.ResourceBundle;

import org.apache.log4j.Logger;

import com.microsoft.sqlserver.jdbc.SQLServerDataSource;

public class SQLConnection {

private static Connection acon = null; 
private static CallableStatement _cs = null; 
private static String _dbServer = null; 
private static String _dbUsername =  null; 
private static String _dbPassword = null;
    private static String _dbName = null;
private static String _dbInstance = null;
private static String _dbWindowsAuthentication = null;


    private static final Logger aLogger = Logger.getLogger(SQLConnection.class.getName());
//  static ResourceBundle resource = ResourceBundle.getBundle("Resource");






 public SQLConnection() {
        _dbServer = "localhost"; 
        _dbUsername = "NewLocationTestUser";
        _dbPassword = "TestPass123";
        _dbName = "NewLocationDB";
        _dbInstance = "APPSQL";
        _dbWindowsAuthentication = "FALSE";
    }

 public Connection getConnection() {

        SQLServerDataSource ds = new SQLServerDataSource();
        Properties properties = new Properties();

        try {
            String dbURL = "jdbc:sqlserver://" + _dbServer;
            if(!_dbInstance.equalsIgnoreCase(""))
            {
                dbURL += "\\" + _dbInstance;
            }
            if(_dbWindowsAuthentication.equalsIgnoreCase("TRUE"))
            {
                dbURL += ";integratedSecurity=true";
            }
            else
            {
                properties.put("user", _dbUsername);
                properties.put("password", _dbPassword);
            }
            dbURL += ";";
            properties.put("database", _dbName);
            acon = DriverManager.getConnection(dbURL, properties);
            System.out.println("1");


         } catch (Exception e) {
             aLogger.error(e.getMessage());
         }
         finally {
            ds = null;
         }
        aLogger.info("The sql connection has been established.");
        return acon;
 }

 public int insertLocations(Timestamp RunDate, String rlpCompanyid, String rlpLocationid,  String rlpOpenDate){

     int returnVal = 0; 

            try{ 

                _cs = getConnection().prepareCall("{call iCurrentLocations01(?, ?, ?, ?)}");
                _cs.setTimestamp("RunDate", RunDate);
                _cs.setString("CompanyId", rlpCompanyid);
                _cs.setString("LocationId", rlpLocationid);
                _cs.setString("rlpOpenDate", rlpOpenDate );
                returnVal = _cs.executeUpdate(); 
                System.out.println("2");

            }catch (SQLException e){
                aLogger.error(e.getMessage());
                }finally {
                    if (_cs != null){ 
                        try{ 
                            _cs.close();
                        }catch(SQLException e) { 
                            aLogger.error(e.getMessage());
                        }
                    }
                 }
            return returnVal;
            }

So when i attempt to run my harness, the connection is made. However, when the program attempts to call my stored procedure "iCurrentLocations01". It returns the error message in my logs

" 2016-01-27 13:11:17 ERROR SQLConnection:97 - Parameter RunDate was not defined for stored procedure iCurrentLocations01."

Can someone please explain what i am doing wrong here? The program btw is taking information from a LDAP directory and inserting it into a local DB.

Edit - This is my stored procedure:

USE [NewLocationDB]
GO

/****** Object:  StoredProcedure [dbo].[iCurrentLocations01]    Script Date:     01/27/2016 1:27:10 PM ******/
SET ANSI_NULLS ON
GO

SET QUOTED_IDENTIFIER ON
GO




ALTER PROCEDURE [dbo].[iCurrentLocations01]
@RunDate datetime, 
@CompanyId varchar, 
@LocationId varchar, 
@rlpOpenDate varchar 

AS 
DECLARE @RetVal int 
SET @RetVal = 0 

INSERT CurrentLocations (RunDate, CompanyId, LocationId, rlpOpenDate )
VALUES (@RunDate, @CompanyId, @LocationId, @rlpOpenDate)

SET @RetVal = @@ERROR
Return @RetVal

GO

回答1:


This may not be exactly what you were hoping for, but it does work for passing parameters to the stored procedure by name, thereby allowing us to

  • specify the parameters in an arbitrary order in the command text, and
  • omit parameters that have default values.

For the stored procedure

CREATE PROCEDURE [dbo].[my_sp] 
    @p1 nvarchar(10) = N'Hello', 
    @p2 nvarchar(10) = N'world'
AS
BEGIN
    SET NOCOUNT ON;
    SELECT @p1 + N', ' + @p2 + N'!' AS response;
END

the JDBC call

try (CallableStatement s = conn.prepareCall("{CALL my_sp (@p2=?)}")) {
    s.setString(1, "Gord");
    try (ResultSet rs = s.executeQuery()) {
        rs.next();
        System.out.println(rs.getString("response"));
    }
}

returns

Hello, Gord!

(Tested with Microsoft JDBC Driver 4.1 for SQL Server.)




回答2:


Use index based set methods.

           _cs = getConnection().prepareCall("{call iCurrentLocations01(?, ?, ?, ?)}");
            _cs.setTimestamp(1, RunDate);
            _cs.setString(2, rlpCompanyid);
            _cs.setString(3, rlpLocationid);
            _cs.setString(4, rlpOpenDate );
            returnVal = _cs.executeUpdate(); 
            System.out.println("2");


来源:https://stackoverflow.com/questions/61264151/java-callablestatement-with-named-parameters-raises-incorrect-syntax-near

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!