使用Oracle.ManagedDataAccess.Client将函数中的值返回到c#

时间:2016-07-26 13:34:50

标签: c# oracle

我在Oracle中有以下功能:

FUNCTION return_test (p_id varchar2) RETURN VARCHAR2
is
   p_return_val VARCHAR2 (500 CHAR) := 'test';
begin  
   return p_return_val;
end;

我试图将值放入我的c#代码中,如下所示:

var dbCommand = new OracleCommand();
string retVal;
string Function_query = "PKG_TEST.return_test";
dbConnection = new OracleConnection(ConnString);
dbConnection.Open();


OracleParameterCollection dbParams = dbCommand.Parameters;
dbParams.Add("p_return_val", OracleDbType.Varchar2, System.Data.ParameterDirection.ReturnValue);
dbParams.Add("p_id", OracleDbType.Varchar2, "123", System.Data.ParameterDirection.Input); 

OracleCommand cmd;
OracleParameter dbAddParam;
cmd = new OracleCommand(Function_query , dbConnection); 
cmd.CommandType = CommandType.StoredProcedure;
foreach (OracleParameter dbParam in dbParams)
{
    dbAddParam = (OracleParameter)dbParam.Clone(); // clones all settings
    cmd.Parameters.Add(dbAddParam);
}
retVal = cmd.ExecuteScalar().tostring();

调试时出错:

  

{" ORA-06502:PL / SQL:数字或值错误:字符串缓冲区   太小\ nORA-06512:第1行"}

2 个答案:

答案 0 :(得分:0)

我从未与OracleParameterCollection合作过。通常我会逐一将Parameters添加到OracleCommand

无论如何,试试这个:

OracleParameterCollection dbParams = dbCommand.Parameters;

dbParams.Add("p_return_val", OracleDbType.Varchar2, 500, null, ParameterDirection.ReturnValue);
dbParams.Parameters["p_return_val"].DbType = DbType.String; // Maybe this line is not required at Oracle.ManagedDataAccess. However, you must use it for Oracle.DataAccess

dbParams.Add("p_id", OracleDbType.Varchar2, "123", ParameterDirection.Input); 

string Function_query = "BEGIN :p_return_val := PKG_TEST.return_test(:p_id); END;";
cmd = new OracleCommand(Function_query , dbConnection);     
cmd.CommandType = CommandType.Text
cmd.Parameters.Add(dbParams);

cmd.ExecuteNonQuery();
retval = cmd.Parameters["p_return_val"].Value;

您不能在函数调用中使用方法ExecuteScalar(),它仅用于结果集,即SELECT ...语句。见Data Provider for .NET Developer's Guide

答案 1 :(得分:0)

谢谢Wernfried的贡献。我现在就试试吧。与此同时,我们发现了这一点:

string query = "select PKG_TEST.return_test(:x) from dual";
dbParams.Add("x", OracleDbType.Varchar2, QuoteID, System.Data.ParameterDirection.Input);
var result = (string)dbManager.ExecuteScalar(query, dbParams, CommandType.Text);

对我来说,它似乎是我的内联SQL,我总是会尝试避免,但它有效。有什么理由我不会用这个吗?