C# 从asp.net向Oracle发送带有逗号的字符串似乎会导致问题
在我的前端,我发送VarChar变量以用于Oracle中的存储过程。我的前端代码如下所示:C# 从asp.net向Oracle发送带有逗号的字符串似乎会导致问题,c#,asp.net,oracle,C#,Asp.net,Oracle,在我的前端,我发送VarChar变量以用于Oracle中的存储过程。我的前端代码如下所示: protected void Page_Load(object sender, EventArgs e) { OracleConnection conn = GetConnection(); try { { string vw_AuditID = Convert.ToString(Request.QueryString["AuditID"]
protected void Page_Load(object sender, EventArgs e)
{
OracleConnection conn = GetConnection();
try
{
{
string vw_AuditID = Convert.ToString(Request.QueryString["AuditID"]);
string vw_PlanID = Convert.ToString(Request.QueryString["PlanID"]);
conn.ConnectionString = ConfigurationManager.ConnectionStrings["ConnCST"].ToString();
OracleCommand cmd3 = new OracleCommand();
cmd3.CommandType = CommandType.StoredProcedure;
cmd3.CommandText = "CSTAPP_O.CST_ADMIN_REPORT";
cmd3.Connection = conn;
cmd3.Parameters.Add("RAudit", OracleType.VarChar).Value = vw_AuditID;
cmd3.Parameters.Add("RPlan", OracleType.VarChar).Value = vw_PlanID;
cmd3.Parameters.Add("cursor_", OracleType.Cursor).Direction = ParameterDirection.Output;
var SearchAdapter = new OracleDataAdapter(cmd3);
var ds = new DataSet();
SearchAdapter.Fill(ds);
// Perform the binding.
GridView_AuditReport.DataSource = ds;
GridView_AuditReport.DataBind();
}
}
catch (Exception ex)
{
// Handle the error
Console.WriteLine("Error making Call to " + ex + "");
}
}
create or replace PROCEDURE "CST_ADMIN_REPORT"
(
RAudit VARCHAR2,
RPlan VARCHAR2,
cursor_ OUT SYS_REFCURSOR
) AS
BEGIN
open cursor_ for
SELECT BLAH // Edited the lengthy SELECT section out, no need for it.
Where FAP.Audit_ID = RAudit
AND FAP.Plan_ID in (RPlan)
ORDER BY FAP.PLAN_DESC ASC;
END CST_ADMIN_REPORT;
请注意,auditd和PlanID来自上一页,并按如下方式传递
?试听='10294'和计划ID='322323324'
在Oracle方面,我运行的存储过程如下:
protected void Page_Load(object sender, EventArgs e)
{
OracleConnection conn = GetConnection();
try
{
{
string vw_AuditID = Convert.ToString(Request.QueryString["AuditID"]);
string vw_PlanID = Convert.ToString(Request.QueryString["PlanID"]);
conn.ConnectionString = ConfigurationManager.ConnectionStrings["ConnCST"].ToString();
OracleCommand cmd3 = new OracleCommand();
cmd3.CommandType = CommandType.StoredProcedure;
cmd3.CommandText = "CSTAPP_O.CST_ADMIN_REPORT";
cmd3.Connection = conn;
cmd3.Parameters.Add("RAudit", OracleType.VarChar).Value = vw_AuditID;
cmd3.Parameters.Add("RPlan", OracleType.VarChar).Value = vw_PlanID;
cmd3.Parameters.Add("cursor_", OracleType.Cursor).Direction = ParameterDirection.Output;
var SearchAdapter = new OracleDataAdapter(cmd3);
var ds = new DataSet();
SearchAdapter.Fill(ds);
// Perform the binding.
GridView_AuditReport.DataSource = ds;
GridView_AuditReport.DataBind();
}
}
catch (Exception ex)
{
// Handle the error
Console.WriteLine("Error making Call to " + ex + "");
}
}
create or replace PROCEDURE "CST_ADMIN_REPORT"
(
RAudit VARCHAR2,
RPlan VARCHAR2,
cursor_ OUT SYS_REFCURSOR
) AS
BEGIN
open cursor_ for
SELECT BLAH // Edited the lengthy SELECT section out, no need for it.
Where FAP.Audit_ID = RAudit
AND FAP.Plan_ID in (RPlan)
ORDER BY FAP.PLAN_DESC ASC;
END CST_ADMIN_REPORT;
所以,如果我通过一个计划ID,它运行得非常好。但是,如果我传递多个planid(例如“322323324”),Oracle过程会告诉我该数字无效
有谁能告诉我,我将信息传递给Oracle的方式可能有什么问题吗?Oracle不接受
in(RPlan)
子句中的字符串。不确定这是否是最佳解决方案,但您可以这样解析参数字符串:
in (SELECT REGEXP_SUBSTR(RPlan,'[^,]+', 1, LEVEL)
FROM DUAL
CONNECT BY REGEXP_SUBSTR(RPlan, '[^,]+', 1, LEVEL) IS NOT NULL)
RPlan
是一个绑定变量,是一个单值-即使您输入逗号分隔的字符串,它仍然是一个单值,并且它试图将Plan\u ID
列中的数值与包含数字和逗号的字符串相匹配,并有效地执行以下操作:
AND TO_CHAR( FAP.Plan_ID ) = '322,323,324'
这不会产生匹配
如果要传入数组,请使用集合:
CREATE OR REPLACE TYPE IntList IS TABLE OF INTEGER;
/
并将其传递到程序中:
create or replace PROCEDURE CST_ADMIN_REPORT
(
RAudit IN FAP.Audit_ID%TYPE,
RPlan IN IntList,
cursor_ OUT SYS_REFCURSOR
) AS
BEGIN
open cursor_ for
SELECT BLAH // Edited the lengthy SELECT section out, no need for it.
Where FAP.Audit_ID = RAudit
AND FAP.Plan_ID MEMBER OF RPlan
ORDER BY FAP.PLAN_DESC ASC;
END CST_ADMIN_REPORT;
但是,您可能会发现C#驱动程序只支持传递(而不是集合),因此您可能需要传递关联数组(可以在PL/SQL中使用,但不能在SQL中使用),并将值复制到集合中,然后在SQL语句中使用:
CREATE OR REPLACE PACKAGE CST_ADMIN_PKG
IS
TYPE IntAssocArrayType IS TABLE OF INTEGER INDEX BY PLS_INTEGER;
PROCEDURE CST_ADMIN_REPORT
(
RAudit IN FAP.Audit_ID%TYPE,
RPlan IN IntAssocArrayType,
cursor_ OUT SYS_REFCURSOR
);
END;
/
CREATE OR REPLACE PACKAGE BODY CST_ADMIN_PKG
IS
PROCEDURE CST_ADMIN_REPORT
(
RAudit IN FAP.Audit_ID%TYPE,
RPlan IN IntAssocArrayType, -- Pass assoc. array in.
cursor_ OUT SYS_REFCURSOR
)
AS
-- Create a collection
p_rplan IntList := IntList();
i PLS_INTEGER;
BEGIN
-- Copy assoc. array into the collection
i := RPlan.FIRST:
WHILE i IS NOT NULL LOOP
p_rplan.EXTEND;
p_rplan(p_rplan.COUNT) := RPlan(i);
i := RPlan.NEXT(i);
END LOOP;
open cursor_ for
SELECT BLAH
Where FAP.Audit_ID = RAudit
AND FAP.Plan_ID MEMBER OF p_RPlan -- Use the collection in the select.
ORDER BY FAP.PLAN_DESC ASC;
END CST_ADMIN_REPORT;
END;
/
当你说“前端代码”,然后把数据库访问混为一谈时,我会退缩。数据库访问并不是直接在你的代码后面——它应该在一个单独的层中。您需要学习如何正确处理(您的OracleConnection)。正如我在中所解释的,请将您的问题分开。这个问题要么与查询字符串有关,要么与Oracle有关,而不是两者都有。查询字符串不了解Oracle,反之亦然。这都是关于字符串的,所以把你的问题精简到一个简单的问题。我还逐字解释了错误,而不是你的解释。“甲骨文程序告诉我数字无效”并不是一个逐字逐句的错误。我一直对一些人所拥有的知识感到惊讶和谦卑。如果我对甲骨文所知甚少,我永远也不会明白这一点。