我正在尝试创建一个接受查询及其参数的函数,并返回一个SQLDataSource以进一步绑定。
功能是:
public static SqlDataSource getSqlSource(string sql, Dictionary<string, string> parameters)
{
SqlConnection con = new SqlConnection(ConnectionString);
using (SqlCommand cmd = con.CreateCommand())
{
con.Open();
cmd.CommandText = sql;
foreach (KeyValuePair<string, string> item in parameters)
{
cmd.Parameters.Add(new SqlParameter(item.Key, item.Value));
}
SqlDataSource source = new SqlDataSource(ConnectionString, cmd.CommandText);
con.Close();
return source;
}
}
我想要创建的查询是:
string sql =
// "declare @from date ; " +
"with cte as " +
"( " +
"select username,count(username) as cc from SaleReport " +
"group by username " +
") " +
"select count(SaleReport.username) as numerKlientesh,distributorname from SaleReport " +
"inner join cte on SaleReport.username=cte.username " +
"where (SaleReport.saledate) <=CONVERT(date,@from) " +
"and (SaleReport.saledate)>=(dateadd(DAY,-10,CONVERT(date,@from))) " +
"and cc>1 and SaleReport.comboid not in (43,44,46,47) " +
"group by distributorname ";
Dictionary<String, String> Params = new Dictionary<String, String>();
Params.Add("@from", from);
SqlDataSource source = QueryManager.getSqlSource(sql, Params);
GridView1.DataSource = source;
GridView1.DataBind();
运行应用程序时,出现以下错误:
“必须声明变量@from”
但是,当我尝试声明它时(我已将声明作为注释)我收到此消息:
变量名'@from'已经被声明。
变量名在查询批处理或存储过程中必须是唯一的。
我在查询中做错了吗?
EDIT1: 根据SabinBio的建议,我输出了查询结果如下:
declare @from date;
with cte as (
select username
,count(username) as cc
from SaleReport
group by username
)
select count(SaleReport.username) as numerKlientesh
,distributorname
from SaleReport
inner join cte on SaleReport.username=cte.username
where (SaleReport.saledate) <= CONVERT(date,@from)
and (SaleReport.saledate) >= (dateadd(DAY,-10,CONVERT(date,@from)))
and cc>1
and SaleReport.comboid not in (43,44,46,47)
group by distributorname
EDIT2
如果我将查询放在存储过程中,我将其称为:
DECLARE @return_value int EXEC @return_value = [dbo].[ProcedureName] @from ="+from+"
它工作正常,但我想避免可能的Sql注入,如果我声明它:
DECLARE @return_value int EXEC @return_value = [dbo].[ProcedureName] @from =@saledate
并将saledate作为我的词典中的项目我仍然有错误
必须声明变量@saledate
答案 0 :(得分:1)
你的cmd.ExecuteReader()
位置错误:
foreach (KeyValuePair<string, string> item in parameters)
{
cmd.Parameters.Add(new SqlParameter(item.Key, item.Value));
cmd.ExecuteReader();
}
我希望这需要像:
foreach (KeyValuePair<string, string> item in parameters)
{
cmd.Parameters.Add(new SqlParameter(item.Key, item.Value));
}
cmd.ExecuteReader();
答案 1 :(得分:1)
经过一段时间的研究,我改变了以下功能:
public static SqlDataSource getSqlSource(string sql, Dictionary<string, string> parameters)
{
SqlConnection con = new SqlConnection(ConnectionString);
SqlDataSource source = new SqlDataSource(ConnectionString, sql);
foreach (KeyValuePair<string,string> pair in parameters)
{
source.SelectParameters.Add(pair.Key, pair.Value);
}
return source;
}
当在后面的代码中声明字典时,Key项不应该用“@”字符声明,“@”字符只能在查询中声明,因此,声明是:
Dictionary<String, String> Params = new Dictionary<String, String>();
Params.Add("from", from);
建议HERE 谢谢大家的帮助:))