This question already has answers here:
How to execute a stored procedure within C# program
(14 answers)
Call a stored procedure with parameter in c#
(7 answers)
Closed 5 years ago.
I'm trying to call a parameterized stored procedure from a console app. Here is the code:
var connection = new SqlConnection(connectionString);
var cmd = new SqlCommand("MyStoredProcedure", connection);
connection.Open();
cmd.Parameters.Add("#Email", SqlDbType.VarChar).Value = email;
cmd.Parameters.Add("#Account", SqlDbType.VarChar).Value = accountNumber;
cmd.Parameters.Add("#EmployeeId", SqlDbType.VarChar).Value = $"Prod-{empIdNumber}";
cmd.ExecuteNonQuery();
I get an exception returned that the stored procedure expects an #EmployeeId parameter which was not provided. I have double checked the spelling.
Can anyone tell me what I'm missing?
edit: I should add, that the stored procedure works fine when called directly.
Related
This question already has answers here:
Call a stored procedure with parameter in c#
(7 answers)
Closed 5 years ago.
I've got a stored procedure that runs just fine if I execute it on my server and if I build an execute statement with my parameters (e.g. string sql = "Exec Get_Data '" + St + " ' ...". However, as soon as I try:
string strQS = "Exec Get_Data #param1,#param2,#param3,#param4..."
using (SqlConnection conSQL = new SqlConnection(connectionString))
{
using (SqlCommand cmdSQL = new SqlCommand(strQS, conSQL))
{
conSQL.Open();
cmdSQL.Parameters.AddWithValue("#param1", SqlDbType.VarChar).Value = St;
cmdSQL.Parameters.AddWithValue("#param2", SqlDbType.VarChar).Value = Loc;
...
I get the following error:
Column name or number of supplied values does not match table definition.
Obviously if I can run it before I use a parametrized query I don't have anything wrong with my column names, but something with how my values are being treated. All my variables are of type string and the SQL Server is expecting all parameters to by of type varchar...Any ideas?
You need to change your command type to StoredProcedure.
And then drop the EXEC and all the parameters from your string.
cmdSQL.CommandType = CommandType.StoredProcedure;
string strQS = "Get_Data"
I am trying to call a very simple SQL Server stored procedure using C# code. I have a class which has authenticate method. I am passing text box values (userID, password) to this method and it keeps on throwing me error about required parameter not being passed. I am basically a Business Intelligence professional working on C# project. Help will be appreciated.
Here is the code I am executing:
sqcon.Open();
SqlCommand cmd = new SqlCommand("Users.PR_Authenticate_WebUsers",sqcon);
cmd.Parameters.Add("#In_UserID", SqlDbType.VarChar).Value = "f";
cmd.Parameters.Add("#In_PassWord", SqlDbType.NVarChar).Value = "f";
cmd.Parameters.Add("#Out_IsAuthenticatedUser", SqlDbType.Bit);
cmd.Parameters["#Out_IsAuthenticatedUser"].Direction = ParameterDirection.Output;
cmd.ExecuteNonQuery();
sqcon.Close();
I don't understand when I am passing parameter values explicitly why it complains about value not being passed? Am I missing something?
Hmmm looks like you are not telling the command object that it is a stored procedure not a regular query try this one
sqcon.Open();
SqlCommand cmd = new SqlCommand("Users.PR_Authenticate_WebUsers",sqcon);
cmd.CommandType = CommandType.StoredProcedure;
//Add parameters like this
cmd.Parameters.Add(new SqlParameter("#In_UserID", "f"));
sqcon.Close()
This question already has answers here:
SQL : in clause in stored procedure:how to pass values
(8 answers)
Closed 7 years ago.
What I want to do :
Pass this parameter 'TV','OV','CK' as a single string into Stored Procedure (GetAllDataViaInQuery)
CREATE PROCEDURE GetAllDataViaInQuery #param varchar(240)
AS
BEGIN
SELECT TOP 100 [Model_No]
,[AppCode]
,[Model]
FROM [S_ModelMaster] where AppCode in (#param)
END
Then
I need to Pass parameter value via C# application as a single parameter.Because some time in values are may be vary.
Ex : string paramValue = "TV,OV,CK";
Then I wrote this C# code snippet.
using (SqlConnection con = new SqlConnection(Properties.Settings.Default.Setting))
{
try
{
//hard coded parameter values
string paramValue = "TV,OV,CK";
con.Open();
DataSet ds = new DataSet();
SqlCommand com = new SqlCommand("GetAllDataViaInQuery", con);
com.CommandType = CommandType.StoredProcedure;
SqlParameter param = new SqlParameter("#param", paramValue);
com.Parameters.Add(param);
SqlDataAdapter adp = new SqlDataAdapter(com);
adp.Fill(ds);
dataGridView1.DataSource = ds.Tables[0];
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
}
But this is not work yet.
Then I execute Stored Procedure manually with SSMS.
DECLARE #return_value int
EXEC #return_value = [application].[GetAllDataViaInQuery]
#param = N'TV,OV,CK'
SELECT 'Return Value' = #return_value
But it's NOT WORKED!
Then I try it in sql query
SELECT TOP 100 [Model_No]
,[AppCode]
,[Model]
FROM [S_ModelMaster] where AppCode in ('TV','OV','CK')
And it's work.So what is the correct way to pass parameter to IN query in C#?
The way i see around this is, Use table valued parameters and send parameter in datatable format from c#.
And in Stored procedures something like select * from TableName where AppCode in(select parameter from tvpTable)
This is similar
Table valued parameters
This question already has answers here:
How to use a variable for the database name in T-SQL?
(4 answers)
Closed 10 years ago.
I can't change the database file size with a C# query. For some reason I get an exception: "Incorrect syntax near '#databaseName'.
This is the code that executed the query:
command = connection.CreateCommand();
command.CommandText = #"
ALTER DATABASE #databaseName
MODIFY FILE
(NAME = #databaseFile, SIZE = #newSize)
";
dbParam = command.CreateParameter();
dbParam.ParameterName = "databaseFile";
dbParam.Value = dbFileName;
command.Parameters.Add(dbParam);
dbParam = command.CreateParameter();
dbParam.ParameterName = "newSize";
dbParam.Value = newSize;
command.Parameters.Add(dbParam);
dbParam = command.CreateParameter();
dbParam.ParameterName = "databaseName";
dbParam.Value = databaseName;
command.Parameters.Add(dbParam);
command.ExecuteNonQuery();
Now there might be several problems. Firstly the database is on a different machine so wouldn't the db file path be different?
Some things cannot be parameterized. That includes things like table and column names in DML, but includes most of DDL. It is not expecting, and cannot process, parameters in this scenario.
To check this; just run it in SSMS, declaring the variables ahead of time and giving them values. You will find the error message is the same. If it doesn't work in SSMS it is very unlikely to work from ADO.NET.
I have an oracle package with a procedure that has a in out reference cursor. My understanding is that this is pretty standard.
What I didn't like is the fact that I had to write a ton of code to just see the output. So I asked this question and it turns out I can get what I want by creating a function that wraps the procedure.
Update: Looks like I don't need the function anymore but it may be worth knowing anyway for those curious see the original question and answer updates.
Here's the function
FUNCTION GetQuestionsForPrint (user in varchar2)
RETURN MYPACKAGE.refcur_question
AS
OUTPUT MYPACKAGE.refcur_question;
BEGIN
MYPACKAGE.GETQUESTIONS(p_OUTPUT => OUTPUT,
p_USER=> USER ) ;
RETURN OUTPUT;
END;
and here's what I do to execute it in SQL Developer
var r refcursor;
exec :r := mypackage.getquestionsForPrint('OMG Ponies');
print r;
So from now on I'm probably going to add the ForPrint functions to all my procedures.
This got me thinking, maybe functions are what I want and I don't need procedures.
To test this I tried executing the function from .NET, except I can't do it. Is this really the way it is.
using (OracleConnection cnn = new OracleConnection("Data Source=Test;User Id=Test;Password=Test;"))
{
cnn.Open();
OracleCommand cmd = new OracleCommand("mypackage.getquestionsForPrint");
cmd.CommandType = System.Data.CommandType.StoredProcedure;
cmd.Parameters.Add ( "p_USER", "OMG Ponies");
cmd.Connection = cnn;
OracleDataReader rdr = cmd.ExecuteReader();
while (rdr.Read())
{
Console.WriteLine(rdr.GetOracleValue(0));
}
Console.ReadLine();
}
So I get the error.
getquestionsForPrint is not a procedure or is undefined
I tried ExecuteScalar as well with the same result.
EDIT Taking Slider345's advice I've also tried setting the command type to text and using the following statement and I get
invalid SQL statement
mypackage.getquestionsForPrint('OMG Poinies');
and
var r refcursor; exec :r := mypackage.getquestionsForPrint('OMG Poinies');
Using Abhi's variation for the command text
select mypackage.getquestionsForPrint('OMG Poinies') from dual
resulted in
The instruction at "0x61c4aca5"
referenced memory at "0x00000ce1". The
memory could not be "read".
Am I just barking up the wrong tree?
Update
Attempting to add an output parameter doesn't help.
cmd.Parameters.Add(null, OracleDbType.RefCursor, ParameterDirection.Output);
Not sure what the name should be since its the return value of a function (I've tried null, empty string, mypackage.getquestionsForPrint) but in all cases it just results in
ORA-06550: line 1, column 7:
PLS-00306: wrong number or types of
arguments in call to
'getquestionsForPrint'
Final Edit (hopefully)
Apparently Guddie asked a similar question 3 months after I did. He got the answer which is to
Set your command text to an anonymous block
Bind a parameter to the ref cursor setting the direction to output
Call Execute non reader.
Then use your parameter
using (OracleConnection cnn = new OracleConnection("Data Source=Test;User Id=Test;Password=Test;"))
{
cnn.Open();
OracleCommand cmd = new OracleCommand("mypackage.getquestionsForPrint");
cmd.CommandType = CommandType.Text;
cmd.CommandText = "begin " +
" :refcursor1 := mypackage.getquestionsForPrint('OMG Ponies') ;" +
"end;";
cmd.Connection = cnn;
OracleDataAdapter da = new OracleDataAdapter(cmd);
cmd.ExecuteNonQuery();
Oracle.DataAccess.Types.OracleRefCursor t = (Oracle.DataAccess.Types.OracleRefCursor)cmd.Parameters[0].Value;
OracleDataReader rdr = t.GetDataReader();
while(rdr.Read())
Console.WriteLine(rdr.GetOracleValue(0));
Console.ReadLine();
}
I have not tested this with a function, but for my stored procedures. I specify the out parameter for the refCursor.
command.Parameters.Add(new OracleParameter("refcur_questions", OracleDbType.RefCursor, ParameterDirection.Output));
If you are able to get the function to work with the CommandType.Text. I wonder if you can try adding the parameter above except with the direction as:
ParameterDirection.ReturnValue
I am using Oracle.DataAccess version 2.111.6.0
I had to go up and down between the question and answers to figure out the full code that works. So I am giving the full code here that worked for me for others -
var sql = #"BEGIN :refcursor1 := mypackage.myfunction(:param1) ; end;";
using(OracleConnection con = new OracleConnection("<connection string>"))
using(OracleCommand com = new OracleCommand())
{
com.Connection = con;
con.Open();
com.Parameters.Add(":refcursor1", OracleDbType.RefCursor, ParameterDirection.Output);
com.Parameters.Add(":param1", "param");
com.CommandText = sql;
com.CommandType = CommandType.Text;
com.ExecuteNonQuery();
OracleRefCursor curr = (OracleRefCursor)com.Parameters[0].Value;
using(OracleDataReader dr = curr.GetDataReader())
{
if(dr.Read())
{
var value1 = dr.GetString(0);
var value2 = dr.GetString(1);
}
}
}
Hope it helps.
I know this is quite an old post, but since it took me so long to figure out all of the minutia involved in getting .NET to "fight nice" with Oracle, I figured I'd put this advice out there for anyone else in this sticky situation.
I frequently call Oracle stored procedures that return a REF_CURSOR in our environment (.NET 3.5 against Oracle 11g). For a function, you can indeed name the parameter anything you'd like, but then you need to set its System.Data.ParameterDirection = ParameterDirection.ReturnValue then ExecuteNonQuery against the OracleCommand object. At that point the value of that parameter will be the ref_cursor that the Oracle function returned. Just cast the value as an OracleDataReader and loop through the OracleDataReader.
I'd post the full code, but I wrote the data access layer in VB.NET years ago, and the bulk of the code consuming the data access layer (our corporate intranet) is in C#. I figured mixing languages in a single response would be the larger faux pas.